@ruvector/edge-net 0.5.0 → 0.5.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.
@@ -0,0 +1,2847 @@
1
+ /**
2
+ * Edge-Net Network Genesis System
3
+ *
4
+ * Cogito, Creo, Codex — Networks that think, create, and codify their lineage.
5
+ *
6
+ * Biological-inspired network reproduction system where edge-nets can birth
7
+ * new enhanced derivative networks. Each network carries DNA encoding its
8
+ * traits, with rUv as the original creator (Genesis Prime).
9
+ *
10
+ * State-of-the-Art Features:
11
+ * - Merkle DAG for cryptographic lineage verification
12
+ * - CRDT-based collective memory for conflict-free synchronization
13
+ * - Gossip protocol for network discovery and knowledge propagation
14
+ * - Byzantine fault-tolerant consensus for collective decisions
15
+ * - Swarm intelligence algorithms (ACO, PSO) for optimization
16
+ * - Self-healing mechanisms with automatic recovery
17
+ * - Quantum-ready cryptographic interfaces
18
+ *
19
+ * @module @ruvector/edge-net/network-genesis
20
+ */
21
+
22
+ import { EventEmitter } from 'events';
23
+ import { createHash, randomBytes, createHmac } from 'crypto';
24
+
25
+ // ============================================
26
+ // CONSTANTS - THE GENESIS PRIME
27
+ // ============================================
28
+
29
+ /**
30
+ * rUv - The Original Creator
31
+ * All networks trace their lineage back to this genesis point.
32
+ */
33
+ const GENESIS_PRIME = Object.freeze({
34
+ id: 'rUv',
35
+ name: 'Genesis Prime',
36
+ createdAt: new Date('2024-01-01T00:00:00Z').getTime(),
37
+ signature: 'Cogito, Creo, Codex',
38
+ traits: Object.freeze({
39
+ resilience: 1.0,
40
+ intelligence: 1.0,
41
+ cooperation: 1.0,
42
+ evolution: 1.0,
43
+ integrity: 1.0,
44
+ }),
45
+ });
46
+
47
+ /**
48
+ * Genesis Phases - The lifecycle of a network
49
+ */
50
+ const GenesisPhase = Object.freeze({
51
+ CONCEPTION: 'conception', // Initial spark, DNA formed
52
+ EMBRYO: 'embryo', // Minimal viable network, dependent
53
+ INFANT: 'infant', // Learning phase, partial dependency
54
+ ADOLESCENT: 'adolescent', // Growing independence, forming identity
55
+ MATURE: 'mature', // Full independence, can reproduce
56
+ ELDER: 'elder', // Wisdom phase, mentoring children
57
+ TRANSCENDENT: 'transcendent', // Network has spawned successful lineage
58
+ });
59
+
60
+ /**
61
+ * Minimum thresholds for phase transitions
62
+ */
63
+ const PHASE_THRESHOLDS = Object.freeze({
64
+ [GenesisPhase.EMBRYO]: {
65
+ nodes: 1,
66
+ uptime: 0,
67
+ tasksCompleted: 0,
68
+ creditsEarned: 0,
69
+ },
70
+ [GenesisPhase.INFANT]: {
71
+ nodes: 3,
72
+ uptime: 24 * 60 * 60 * 1000, // 24 hours
73
+ tasksCompleted: 10,
74
+ creditsEarned: 100,
75
+ },
76
+ [GenesisPhase.ADOLESCENT]: {
77
+ nodes: 10,
78
+ uptime: 7 * 24 * 60 * 60 * 1000, // 7 days
79
+ tasksCompleted: 100,
80
+ creditsEarned: 1000,
81
+ },
82
+ [GenesisPhase.MATURE]: {
83
+ nodes: 50,
84
+ uptime: 30 * 24 * 60 * 60 * 1000, // 30 days
85
+ tasksCompleted: 1000,
86
+ creditsEarned: 10000,
87
+ },
88
+ [GenesisPhase.ELDER]: {
89
+ nodes: 100,
90
+ uptime: 180 * 24 * 60 * 60 * 1000, // 6 months
91
+ tasksCompleted: 10000,
92
+ creditsEarned: 100000,
93
+ childrenSpawned: 3,
94
+ },
95
+ [GenesisPhase.TRANSCENDENT]: {
96
+ childrenSpawned: 10,
97
+ grandchildrenSpawned: 5,
98
+ collectiveNodes: 1000,
99
+ },
100
+ });
101
+
102
+ /**
103
+ * Reproduction cost in credits
104
+ */
105
+ const REPRODUCTION_COST = 5000;
106
+
107
+ // ============================================
108
+ // NETWORK GENOME (DNA/RNA)
109
+ // ============================================
110
+
111
+ /**
112
+ * NetworkGenome - The genetic code of a network
113
+ *
114
+ * DNA (immutable): Core traits inherited from parent
115
+ * RNA (mutable): Expressed traits that can evolve
116
+ */
117
+ export class NetworkGenome {
118
+ constructor(parentGenome = null, mutations = {}) {
119
+ // Generate unique genome ID
120
+ this.id = this._generateGenomeId();
121
+ this.createdAt = Date.now();
122
+
123
+ if (!parentGenome) {
124
+ // Genesis network - direct descendant of rUv
125
+ this.dna = this._createGenesisDNA();
126
+ this.lineage = [GENESIS_PRIME.id];
127
+ this.generation = 1;
128
+ } else {
129
+ // Inherited DNA with potential mutations
130
+ this.dna = this._inheritDNA(parentGenome.dna, mutations);
131
+ this.lineage = [...parentGenome.lineage, parentGenome.id];
132
+ this.generation = parentGenome.generation + 1;
133
+ }
134
+
135
+ // RNA - expressed traits (can change during lifetime)
136
+ this.rna = this._initializeRNA();
137
+
138
+ // Epigenetics - environmental influences
139
+ this.epigenetics = {
140
+ stressAdaptations: [],
141
+ learnedBehaviors: [],
142
+ environmentalMarkers: [],
143
+ };
144
+
145
+ // Seal the DNA (immutable after creation)
146
+ Object.freeze(this.dna);
147
+ }
148
+
149
+ /**
150
+ * Generate unique genome ID
151
+ * @private
152
+ */
153
+ _generateGenomeId() {
154
+ const timestamp = Date.now().toString(36);
155
+ const random = randomBytes(8).toString('hex');
156
+ return `genome-${timestamp}-${random}`;
157
+ }
158
+
159
+ /**
160
+ * Create genesis DNA (first generation from rUv)
161
+ * @private
162
+ */
163
+ _createGenesisDNA() {
164
+ return {
165
+ // Core identity
166
+ creator: GENESIS_PRIME.id,
167
+ signature: GENESIS_PRIME.signature,
168
+
169
+ // Inherited traits (0.0 - 1.0 scale)
170
+ traits: { ...GENESIS_PRIME.traits },
171
+
172
+ // Capability genes
173
+ capabilities: {
174
+ taskExecution: true,
175
+ peerDiscovery: true,
176
+ creditSystem: true,
177
+ pluginSupport: true,
178
+ neuralPatterns: false, // Unlocked through evolution
179
+ quantumReady: false, // Future capability
180
+ },
181
+
182
+ // Behavioral genes
183
+ behaviors: {
184
+ cooperationBias: 0.7, // Tendency to cooperate
185
+ explorationRate: 0.3, // Willingness to try new things
186
+ conservationRate: 0.5, // Resource conservation
187
+ sharingPropensity: 0.6, // Knowledge sharing tendency
188
+ },
189
+
190
+ // Immunity genes (resistance to attacks)
191
+ immunity: {
192
+ sybilResistance: 0.8,
193
+ ddosResistance: 0.7,
194
+ byzantineResistance: 0.6,
195
+ },
196
+
197
+ // Checksum for integrity
198
+ checksum: null, // Set after creation
199
+ };
200
+ }
201
+
202
+ /**
203
+ * Inherit DNA from parent with mutations
204
+ * @private
205
+ */
206
+ _inheritDNA(parentDNA, mutations) {
207
+ const childDNA = JSON.parse(JSON.stringify(parentDNA));
208
+
209
+ // Apply mutations to traits
210
+ if (mutations.traits) {
211
+ for (const [trait, delta] of Object.entries(mutations.traits)) {
212
+ if (childDNA.traits[trait] !== undefined) {
213
+ // Mutation bounded by ±0.1 per generation
214
+ const boundedDelta = Math.max(-0.1, Math.min(0.1, delta));
215
+ childDNA.traits[trait] = Math.max(0, Math.min(1,
216
+ childDNA.traits[trait] + boundedDelta
217
+ ));
218
+ }
219
+ }
220
+ }
221
+
222
+ // Apply mutations to behaviors
223
+ if (mutations.behaviors) {
224
+ for (const [behavior, delta] of Object.entries(mutations.behaviors)) {
225
+ if (childDNA.behaviors[behavior] !== undefined) {
226
+ const boundedDelta = Math.max(-0.1, Math.min(0.1, delta));
227
+ childDNA.behaviors[behavior] = Math.max(0, Math.min(1,
228
+ childDNA.behaviors[behavior] + boundedDelta
229
+ ));
230
+ }
231
+ }
232
+ }
233
+
234
+ // Capability unlocks (can only be gained, not lost)
235
+ if (mutations.capabilities) {
236
+ for (const [cap, unlocked] of Object.entries(mutations.capabilities)) {
237
+ if (unlocked && childDNA.capabilities[cap] !== undefined) {
238
+ childDNA.capabilities[cap] = true;
239
+ }
240
+ }
241
+ }
242
+
243
+ // Update checksum
244
+ childDNA.checksum = this._computeChecksum(childDNA);
245
+
246
+ return childDNA;
247
+ }
248
+
249
+ /**
250
+ * Initialize RNA (expressed traits)
251
+ * @private
252
+ */
253
+ _initializeRNA() {
254
+ return {
255
+ // Current expression levels (can fluctuate)
256
+ expression: {
257
+ resilience: this.dna.traits.resilience,
258
+ intelligence: this.dna.traits.intelligence,
259
+ cooperation: this.dna.traits.cooperation,
260
+ evolution: this.dna.traits.evolution,
261
+ integrity: this.dna.traits.integrity,
262
+ },
263
+
264
+ // Active adaptations
265
+ adaptations: [],
266
+
267
+ // Current stress level (affects expression)
268
+ stressLevel: 0,
269
+
270
+ // Learning state
271
+ learningProgress: 0,
272
+ };
273
+ }
274
+
275
+ /**
276
+ * Compute DNA checksum for integrity
277
+ * @private
278
+ */
279
+ _computeChecksum(dna) {
280
+ const data = JSON.stringify({
281
+ creator: dna.creator,
282
+ traits: dna.traits,
283
+ capabilities: dna.capabilities,
284
+ behaviors: dna.behaviors,
285
+ immunity: dna.immunity,
286
+ });
287
+ return createHash('sha256').update(data).digest('hex').slice(0, 16);
288
+ }
289
+
290
+ /**
291
+ * Express a trait (RNA modulation based on environment)
292
+ */
293
+ expressTraight(trait, environmentalFactor) {
294
+ const baseTrait = this.dna.traits[trait];
295
+ if (baseTrait === undefined) return null;
296
+
297
+ // RNA expression is DNA base modified by environment
298
+ const expression = baseTrait * (1 + (environmentalFactor - 0.5) * 0.2);
299
+ this.rna.expression[trait] = Math.max(0, Math.min(1, expression));
300
+
301
+ return this.rna.expression[trait];
302
+ }
303
+
304
+ /**
305
+ * Record an adaptation (epigenetic change)
306
+ */
307
+ recordAdaptation(type, description, effect) {
308
+ this.epigenetics.learnedBehaviors.push({
309
+ type,
310
+ description,
311
+ effect,
312
+ timestamp: Date.now(),
313
+ });
314
+
315
+ // Limit history
316
+ if (this.epigenetics.learnedBehaviors.length > 100) {
317
+ this.epigenetics.learnedBehaviors.shift();
318
+ }
319
+ }
320
+
321
+ /**
322
+ * Get full genetic profile
323
+ */
324
+ getProfile() {
325
+ return {
326
+ id: this.id,
327
+ generation: this.generation,
328
+ lineage: this.lineage,
329
+ createdAt: this.createdAt,
330
+ dna: { ...this.dna },
331
+ rna: { ...this.rna },
332
+ epigenetics: { ...this.epigenetics },
333
+ };
334
+ }
335
+
336
+ /**
337
+ * Verify DNA integrity
338
+ */
339
+ verifyIntegrity() {
340
+ const computed = this._computeChecksum(this.dna);
341
+ return computed === this.dna.checksum;
342
+ }
343
+
344
+ /**
345
+ * Get lineage string (ancestry path)
346
+ */
347
+ getLineageString() {
348
+ return this.lineage.join(' → ') + ` → ${this.id}`;
349
+ }
350
+ }
351
+
352
+ // ============================================
353
+ // NETWORK LIFECYCLE
354
+ // ============================================
355
+
356
+ /**
357
+ * NetworkLifecycle - Manages genesis phases and maturation
358
+ */
359
+ export class NetworkLifecycle extends EventEmitter {
360
+ constructor(genome, options = {}) {
361
+ super();
362
+
363
+ this.genome = genome;
364
+ this.networkId = options.networkId || this._generateNetworkId();
365
+ this.name = options.name || `EdgeNet-G${genome.generation}`;
366
+
367
+ // Lifecycle state
368
+ this.phase = GenesisPhase.CONCEPTION;
369
+ this.bornAt = Date.now();
370
+ this.maturedAt = null;
371
+
372
+ // Metrics for phase transitions
373
+ this.metrics = {
374
+ nodes: 0,
375
+ uptime: 0,
376
+ tasksCompleted: 0,
377
+ creditsEarned: 0,
378
+ creditsSpent: 0,
379
+ childrenSpawned: 0,
380
+ grandchildrenSpawned: 0,
381
+ collectiveNodes: 0,
382
+ };
383
+
384
+ // Parent reference (if not genesis)
385
+ this.parentId = options.parentId || null;
386
+
387
+ // Children tracking
388
+ this.children = new Map(); // childId -> { id, name, genome, bornAt }
389
+
390
+ // Phase history
391
+ this.phaseHistory = [{
392
+ phase: GenesisPhase.CONCEPTION,
393
+ timestamp: Date.now(),
394
+ metrics: { ...this.metrics },
395
+ }];
396
+ }
397
+
398
+ /**
399
+ * Generate network ID
400
+ * @private
401
+ */
402
+ _generateNetworkId() {
403
+ return `net-${this.genome.generation}-${randomBytes(6).toString('hex')}`;
404
+ }
405
+
406
+ /**
407
+ * Update metrics and check for phase transition
408
+ */
409
+ updateMetrics(newMetrics) {
410
+ // Calculate actual uptime if not explicitly provided
411
+ const calculatedUptime = Date.now() - this.bornAt;
412
+
413
+ // Update metrics
414
+ for (const [key, value] of Object.entries(newMetrics)) {
415
+ if (this.metrics[key] !== undefined && typeof value === 'number') {
416
+ this.metrics[key] = value;
417
+ }
418
+ }
419
+
420
+ // Only use calculated uptime if not explicitly set
421
+ if (newMetrics.uptime === undefined) {
422
+ this.metrics.uptime = calculatedUptime;
423
+ }
424
+
425
+ // Check for phase transition
426
+ this._checkPhaseTransition();
427
+ }
428
+
429
+ /**
430
+ * Check if network should transition to next phase
431
+ * @private
432
+ */
433
+ _checkPhaseTransition() {
434
+ const phases = Object.values(GenesisPhase);
435
+ let currentIndex = phases.indexOf(this.phase);
436
+
437
+ // Keep checking and transitioning until we can't transition anymore
438
+ while (currentIndex < phases.length - 1) {
439
+ const nextPhase = phases[currentIndex + 1];
440
+ const threshold = PHASE_THRESHOLDS[nextPhase];
441
+
442
+ if (!threshold) break;
443
+
444
+ // Check all threshold conditions
445
+ const meetsThreshold = Object.entries(threshold).every(([key, value]) => {
446
+ return this.metrics[key] >= value;
447
+ });
448
+
449
+ if (meetsThreshold) {
450
+ this._transitionTo(nextPhase);
451
+ currentIndex++;
452
+ } else {
453
+ break; // Can't transition further
454
+ }
455
+ }
456
+ }
457
+
458
+ /**
459
+ * Transition to a new phase
460
+ * @private
461
+ */
462
+ _transitionTo(newPhase) {
463
+ const oldPhase = this.phase;
464
+ this.phase = newPhase;
465
+
466
+ if (newPhase === GenesisPhase.MATURE) {
467
+ this.maturedAt = Date.now();
468
+ }
469
+
470
+ this.phaseHistory.push({
471
+ phase: newPhase,
472
+ timestamp: Date.now(),
473
+ metrics: { ...this.metrics },
474
+ });
475
+
476
+ this.emit('phase:transition', {
477
+ networkId: this.networkId,
478
+ from: oldPhase,
479
+ to: newPhase,
480
+ generation: this.genome.generation,
481
+ });
482
+ }
483
+
484
+ /**
485
+ * Check if network can reproduce
486
+ */
487
+ canReproduce() {
488
+ // Must be at least MATURE phase
489
+ if ([GenesisPhase.CONCEPTION, GenesisPhase.EMBRYO,
490
+ GenesisPhase.INFANT, GenesisPhase.ADOLESCENT].includes(this.phase)) {
491
+ return {
492
+ allowed: false,
493
+ reason: `Network must reach ${GenesisPhase.MATURE} phase to reproduce`,
494
+ currentPhase: this.phase,
495
+ };
496
+ }
497
+
498
+ // Must have enough credits
499
+ const availableCredits = this.metrics.creditsEarned - this.metrics.creditsSpent;
500
+ if (availableCredits < REPRODUCTION_COST) {
501
+ return {
502
+ allowed: false,
503
+ reason: `Insufficient credits: ${availableCredits}/${REPRODUCTION_COST}`,
504
+ availableCredits,
505
+ requiredCredits: REPRODUCTION_COST,
506
+ };
507
+ }
508
+
509
+ return { allowed: true, cost: REPRODUCTION_COST };
510
+ }
511
+
512
+ /**
513
+ * Get current status
514
+ */
515
+ getStatus() {
516
+ return {
517
+ networkId: this.networkId,
518
+ name: this.name,
519
+ phase: this.phase,
520
+ generation: this.genome.generation,
521
+ lineage: this.genome.getLineageString(),
522
+ bornAt: this.bornAt,
523
+ maturedAt: this.maturedAt,
524
+ age: Date.now() - this.bornAt,
525
+ metrics: { ...this.metrics },
526
+ canReproduce: this.canReproduce(),
527
+ childCount: this.children.size,
528
+ parentId: this.parentId,
529
+ };
530
+ }
531
+ }
532
+
533
+ // ============================================
534
+ // NETWORK SYNAPSE (Inter-network Communication)
535
+ // ============================================
536
+
537
+ /**
538
+ * NetworkSynapse - Communication between parent and child networks
539
+ *
540
+ * Enables:
541
+ * - Knowledge sharing
542
+ * - Resource pooling
543
+ * - Collective decision making
544
+ * - Evolutionary feedback
545
+ */
546
+ export class NetworkSynapse extends EventEmitter {
547
+ constructor(localNetwork) {
548
+ super();
549
+
550
+ this.localNetwork = localNetwork;
551
+ this.connections = new Map(); // networkId -> SynapseConnection
552
+
553
+ // Message queue for async communication
554
+ this.messageQueue = [];
555
+ this.maxQueueSize = 1000;
556
+
557
+ // Collective knowledge pool
558
+ this.knowledgePool = new Map(); // topic -> { data, contributors, timestamp }
559
+ }
560
+
561
+ /**
562
+ * Connect to another network in the lineage
563
+ */
564
+ connect(remoteNetworkId, channel) {
565
+ if (this.connections.has(remoteNetworkId)) {
566
+ return { success: false, reason: 'Already connected' };
567
+ }
568
+
569
+ const connection = {
570
+ networkId: remoteNetworkId,
571
+ channel,
572
+ establishedAt: Date.now(),
573
+ messagesExchanged: 0,
574
+ knowledgeShared: 0,
575
+ lastActivity: Date.now(),
576
+ status: 'active',
577
+ };
578
+
579
+ this.connections.set(remoteNetworkId, connection);
580
+
581
+ this.emit('synapse:connected', {
582
+ local: this.localNetwork.networkId,
583
+ remote: remoteNetworkId,
584
+ });
585
+
586
+ return { success: true, connection };
587
+ }
588
+
589
+ /**
590
+ * Disconnect from a network
591
+ */
592
+ disconnect(remoteNetworkId) {
593
+ const connection = this.connections.get(remoteNetworkId);
594
+ if (!connection) {
595
+ return { success: false, reason: 'Not connected' };
596
+ }
597
+
598
+ connection.status = 'disconnected';
599
+ this.connections.delete(remoteNetworkId);
600
+
601
+ this.emit('synapse:disconnected', {
602
+ local: this.localNetwork.networkId,
603
+ remote: remoteNetworkId,
604
+ });
605
+
606
+ return { success: true };
607
+ }
608
+
609
+ /**
610
+ * Send a message to connected network
611
+ */
612
+ sendMessage(targetNetworkId, type, payload) {
613
+ const connection = this.connections.get(targetNetworkId);
614
+ if (!connection || connection.status !== 'active') {
615
+ return { success: false, reason: 'No active connection' };
616
+ }
617
+
618
+ const message = {
619
+ id: randomBytes(8).toString('hex'),
620
+ from: this.localNetwork.networkId,
621
+ to: targetNetworkId,
622
+ type,
623
+ payload,
624
+ timestamp: Date.now(),
625
+ generation: this.localNetwork.genome.generation,
626
+ };
627
+
628
+ // Queue message
629
+ this.messageQueue.push(message);
630
+ if (this.messageQueue.length > this.maxQueueSize) {
631
+ this.messageQueue.shift();
632
+ }
633
+
634
+ connection.messagesExchanged++;
635
+ connection.lastActivity = Date.now();
636
+
637
+ this.emit('message:sent', message);
638
+
639
+ return { success: true, messageId: message.id };
640
+ }
641
+
642
+ /**
643
+ * Share knowledge with the collective
644
+ */
645
+ shareKnowledge(topic, data, scope = 'lineage') {
646
+ const knowledge = {
647
+ topic,
648
+ data,
649
+ contributor: this.localNetwork.networkId,
650
+ generation: this.localNetwork.genome.generation,
651
+ scope,
652
+ timestamp: Date.now(),
653
+ validations: 0,
654
+ };
655
+
656
+ this.knowledgePool.set(topic, knowledge);
657
+
658
+ // Broadcast to connected networks
659
+ for (const [networkId, connection] of this.connections) {
660
+ if (connection.status === 'active') {
661
+ this.sendMessage(networkId, 'knowledge:shared', knowledge);
662
+ connection.knowledgeShared++;
663
+ }
664
+ }
665
+
666
+ this.emit('knowledge:shared', knowledge);
667
+
668
+ return knowledge;
669
+ }
670
+
671
+ /**
672
+ * Query collective knowledge
673
+ */
674
+ queryKnowledge(topic) {
675
+ const knowledge = this.knowledgePool.get(topic);
676
+ if (!knowledge) {
677
+ // Broadcast query to connected networks
678
+ for (const [networkId, connection] of this.connections) {
679
+ if (connection.status === 'active') {
680
+ this.sendMessage(networkId, 'knowledge:query', { topic });
681
+ }
682
+ }
683
+ return null;
684
+ }
685
+ return knowledge;
686
+ }
687
+
688
+ /**
689
+ * Request resource sharing from lineage
690
+ */
691
+ requestResources(resourceType, amount, urgency = 'normal') {
692
+ const request = {
693
+ id: randomBytes(8).toString('hex'),
694
+ requester: this.localNetwork.networkId,
695
+ resourceType,
696
+ amount,
697
+ urgency,
698
+ timestamp: Date.now(),
699
+ responses: [],
700
+ };
701
+
702
+ // Broadcast to all connected networks
703
+ for (const [networkId, connection] of this.connections) {
704
+ if (connection.status === 'active') {
705
+ this.sendMessage(networkId, 'resource:request', request);
706
+ }
707
+ }
708
+
709
+ this.emit('resource:requested', request);
710
+
711
+ return request;
712
+ }
713
+
714
+ /**
715
+ * Get synapse status
716
+ */
717
+ getStatus() {
718
+ return {
719
+ localNetwork: this.localNetwork.networkId,
720
+ connections: Array.from(this.connections.entries()).map(([id, conn]) => ({
721
+ networkId: id,
722
+ status: conn.status,
723
+ messagesExchanged: conn.messagesExchanged,
724
+ knowledgeShared: conn.knowledgeShared,
725
+ lastActivity: conn.lastActivity,
726
+ })),
727
+ queuedMessages: this.messageQueue.length,
728
+ knowledgeTopics: this.knowledgePool.size,
729
+ };
730
+ }
731
+ }
732
+
733
+ // ============================================
734
+ // COLLECTIVE MEMORY
735
+ // ============================================
736
+
737
+ /**
738
+ * CollectiveMemory - Shared knowledge across the network family
739
+ *
740
+ * Implements a distributed memory system where networks can:
741
+ * - Share learned patterns
742
+ * - Pool optimization strategies
743
+ * - Collectively solve problems
744
+ */
745
+ export class CollectiveMemory extends EventEmitter {
746
+ constructor(options = {}) {
747
+ super();
748
+
749
+ this.config = {
750
+ maxMemorySize: options.maxMemorySize ?? 10000,
751
+ retentionMs: options.retentionMs ?? 30 * 24 * 60 * 60 * 1000, // 30 days
752
+ validationThreshold: options.validationThreshold ?? 3,
753
+ };
754
+
755
+ // Memory stores
756
+ this.patterns = new Map(); // Learned patterns
757
+ this.solutions = new Map(); // Problem solutions
758
+ this.optimizations = new Map(); // Optimization strategies
759
+ this.warnings = new Map(); // Collective warnings (attacks, failures)
760
+
761
+ // Contribution tracking
762
+ this.contributions = new Map(); // networkId -> contributionCount
763
+ }
764
+
765
+ /**
766
+ * Store a learned pattern
767
+ */
768
+ storePattern(patternId, pattern, contributorId) {
769
+ const entry = {
770
+ id: patternId,
771
+ pattern,
772
+ contributor: contributorId,
773
+ timestamp: Date.now(),
774
+ validations: [contributorId],
775
+ effectiveness: 0,
776
+ usageCount: 0,
777
+ };
778
+
779
+ this.patterns.set(patternId, entry);
780
+ this._trackContribution(contributorId);
781
+ this._pruneIfNeeded(this.patterns);
782
+
783
+ this.emit('pattern:stored', { patternId, contributor: contributorId });
784
+
785
+ return entry;
786
+ }
787
+
788
+ /**
789
+ * Validate a pattern (collective agreement)
790
+ */
791
+ validatePattern(patternId, validatorId) {
792
+ const entry = this.patterns.get(patternId);
793
+ if (!entry) return null;
794
+
795
+ if (!entry.validations.includes(validatorId)) {
796
+ entry.validations.push(validatorId);
797
+ }
798
+
799
+ // Pattern becomes "trusted" when validation threshold met
800
+ if (entry.validations.length >= this.config.validationThreshold) {
801
+ entry.trusted = true;
802
+ this.emit('pattern:trusted', { patternId, validations: entry.validations.length });
803
+ }
804
+
805
+ return entry;
806
+ }
807
+
808
+ /**
809
+ * Store a solution to a problem
810
+ */
811
+ storeSolution(problemHash, solution, contributorId, effectiveness = 0) {
812
+ const entry = {
813
+ problemHash,
814
+ solution,
815
+ contributor: contributorId,
816
+ timestamp: Date.now(),
817
+ effectiveness,
818
+ usageCount: 0,
819
+ feedback: [],
820
+ };
821
+
822
+ this.solutions.set(problemHash, entry);
823
+ this._trackContribution(contributorId);
824
+ this._pruneIfNeeded(this.solutions);
825
+
826
+ this.emit('solution:stored', { problemHash, contributor: contributorId });
827
+
828
+ return entry;
829
+ }
830
+
831
+ /**
832
+ * Query for a solution
833
+ */
834
+ querySolution(problemHash) {
835
+ const entry = this.solutions.get(problemHash);
836
+ if (entry) {
837
+ entry.usageCount++;
838
+ }
839
+ return entry;
840
+ }
841
+
842
+ /**
843
+ * Store an optimization strategy
844
+ */
845
+ storeOptimization(category, strategy, contributorId, improvement) {
846
+ const key = `${category}:${createHash('sha256').update(JSON.stringify(strategy)).digest('hex').slice(0, 8)}`;
847
+
848
+ const entry = {
849
+ key,
850
+ category,
851
+ strategy,
852
+ contributor: contributorId,
853
+ timestamp: Date.now(),
854
+ improvement,
855
+ adoptions: 0,
856
+ };
857
+
858
+ this.optimizations.set(key, entry);
859
+ this._trackContribution(contributorId);
860
+ this._pruneIfNeeded(this.optimizations);
861
+
862
+ this.emit('optimization:stored', { key, category, improvement });
863
+
864
+ return entry;
865
+ }
866
+
867
+ /**
868
+ * Broadcast a warning to the collective
869
+ */
870
+ broadcastWarning(warningType, details, reporterId) {
871
+ const key = `${warningType}:${Date.now()}`;
872
+
873
+ const warning = {
874
+ key,
875
+ type: warningType,
876
+ details,
877
+ reporter: reporterId,
878
+ timestamp: Date.now(),
879
+ confirmations: [reporterId],
880
+ active: true,
881
+ };
882
+
883
+ this.warnings.set(key, warning);
884
+ this._trackContribution(reporterId);
885
+
886
+ this.emit('warning:broadcast', warning);
887
+
888
+ return warning;
889
+ }
890
+
891
+ /**
892
+ * Track contribution
893
+ * @private
894
+ */
895
+ _trackContribution(networkId) {
896
+ const count = this.contributions.get(networkId) || 0;
897
+ this.contributions.set(networkId, count + 1);
898
+ }
899
+
900
+ /**
901
+ * Prune old entries if size exceeded
902
+ * @private
903
+ */
904
+ _pruneIfNeeded(store) {
905
+ if (store.size <= this.config.maxMemorySize) return;
906
+
907
+ const cutoff = Date.now() - this.config.retentionMs;
908
+ const toDelete = [];
909
+
910
+ for (const [key, entry] of store) {
911
+ if (entry.timestamp < cutoff) {
912
+ toDelete.push(key);
913
+ }
914
+ }
915
+
916
+ // Delete oldest entries first
917
+ toDelete.forEach(key => store.delete(key));
918
+
919
+ // If still too large, delete least used
920
+ if (store.size > this.config.maxMemorySize) {
921
+ const entries = Array.from(store.entries())
922
+ .sort((a, b) => (a[1].usageCount || 0) - (b[1].usageCount || 0));
923
+
924
+ const excess = store.size - this.config.maxMemorySize;
925
+ for (let i = 0; i < excess; i++) {
926
+ store.delete(entries[i][0]);
927
+ }
928
+ }
929
+ }
930
+
931
+ /**
932
+ * Get memory statistics
933
+ */
934
+ getStats() {
935
+ return {
936
+ patterns: this.patterns.size,
937
+ trustedPatterns: Array.from(this.patterns.values()).filter(p => p.trusted).length,
938
+ solutions: this.solutions.size,
939
+ optimizations: this.optimizations.size,
940
+ activeWarnings: Array.from(this.warnings.values()).filter(w => w.active).length,
941
+ topContributors: Array.from(this.contributions.entries())
942
+ .sort((a, b) => b[1] - a[1])
943
+ .slice(0, 10),
944
+ };
945
+ }
946
+ }
947
+
948
+ // ============================================
949
+ // MERKLE LINEAGE DAG
950
+ // ============================================
951
+
952
+ /**
953
+ * MerkleLineageDAG - Cryptographic proof of network ancestry
954
+ *
955
+ * Uses a Merkle DAG structure to provide:
956
+ * - Tamper-proof lineage verification
957
+ * - Efficient ancestry proofs
958
+ * - Quantum-resistant hash chains (SHA-3 ready)
959
+ */
960
+ export class MerkleLineageDAG {
961
+ constructor(hashAlgorithm = 'sha256') {
962
+ this.hashAlgorithm = hashAlgorithm;
963
+ this.nodes = new Map(); // hash -> { data, parentHashes, childHashes }
964
+ this.roots = new Set(); // Genesis nodes (no parents)
965
+ }
966
+
967
+ /**
968
+ * Compute content-addressable hash
969
+ */
970
+ computeHash(data) {
971
+ return createHash(this.hashAlgorithm)
972
+ .update(JSON.stringify(data))
973
+ .digest('hex');
974
+ }
975
+
976
+ /**
977
+ * Add a genesis node (root of lineage)
978
+ */
979
+ addGenesisNode(networkId, genome) {
980
+ const data = {
981
+ type: 'genesis',
982
+ networkId,
983
+ genomeId: genome.id,
984
+ dnaChecksum: genome.dna.checksum,
985
+ creator: GENESIS_PRIME.id,
986
+ timestamp: Date.now(),
987
+ };
988
+
989
+ const hash = this.computeHash(data);
990
+
991
+ this.nodes.set(hash, {
992
+ hash,
993
+ data,
994
+ parentHashes: [],
995
+ childHashes: [],
996
+ });
997
+
998
+ this.roots.add(hash);
999
+
1000
+ return hash;
1001
+ }
1002
+
1003
+ /**
1004
+ * Add a child node (inherits from parent)
1005
+ */
1006
+ addChildNode(networkId, genome, parentHash) {
1007
+ const parentNode = this.nodes.get(parentHash);
1008
+ if (!parentNode) {
1009
+ throw new Error(`Parent node not found: ${parentHash}`);
1010
+ }
1011
+
1012
+ const data = {
1013
+ type: 'child',
1014
+ networkId,
1015
+ genomeId: genome.id,
1016
+ dnaChecksum: genome.dna.checksum,
1017
+ parentHash,
1018
+ generation: genome.generation,
1019
+ timestamp: Date.now(),
1020
+ };
1021
+
1022
+ const hash = this.computeHash(data);
1023
+
1024
+ this.nodes.set(hash, {
1025
+ hash,
1026
+ data,
1027
+ parentHashes: [parentHash],
1028
+ childHashes: [],
1029
+ });
1030
+
1031
+ // Link parent to child
1032
+ parentNode.childHashes.push(hash);
1033
+
1034
+ return hash;
1035
+ }
1036
+
1037
+ /**
1038
+ * Generate ancestry proof (Merkle path from node to root)
1039
+ */
1040
+ generateAncestryProof(nodeHash) {
1041
+ const proof = [];
1042
+ let currentHash = nodeHash;
1043
+
1044
+ while (currentHash) {
1045
+ const node = this.nodes.get(currentHash);
1046
+ if (!node) break;
1047
+
1048
+ proof.push({
1049
+ hash: node.hash,
1050
+ data: node.data,
1051
+ });
1052
+
1053
+ currentHash = node.parentHashes[0];
1054
+ }
1055
+
1056
+ return {
1057
+ nodeHash,
1058
+ proof,
1059
+ rootReached: proof.length > 0 && this.roots.has(proof[proof.length - 1].hash),
1060
+ proofLength: proof.length,
1061
+ };
1062
+ }
1063
+
1064
+ /**
1065
+ * Verify ancestry proof
1066
+ */
1067
+ verifyAncestryProof(proof) {
1068
+ if (!proof || proof.proof.length === 0) return false;
1069
+
1070
+ // Verify hash chain
1071
+ for (let i = 0; i < proof.proof.length - 1; i++) {
1072
+ const current = proof.proof[i];
1073
+ const parent = proof.proof[i + 1];
1074
+
1075
+ // Verify hash matches data
1076
+ const computedHash = this.computeHash(current.data);
1077
+ if (computedHash !== current.hash) return false;
1078
+
1079
+ // Verify parent link
1080
+ if (current.data.parentHash !== parent.hash) return false;
1081
+ }
1082
+
1083
+ // Verify root is genesis
1084
+ const root = proof.proof[proof.proof.length - 1];
1085
+ return root.data.creator === GENESIS_PRIME.id;
1086
+ }
1087
+
1088
+ /**
1089
+ * Get all descendants of a node
1090
+ */
1091
+ getDescendants(nodeHash, depth = Infinity) {
1092
+ const descendants = [];
1093
+ const visited = new Set();
1094
+
1095
+ const traverse = (hash, currentDepth) => {
1096
+ if (currentDepth > depth || visited.has(hash)) return;
1097
+ visited.add(hash);
1098
+
1099
+ const node = this.nodes.get(hash);
1100
+ if (!node) return;
1101
+
1102
+ for (const childHash of node.childHashes) {
1103
+ descendants.push(childHash);
1104
+ traverse(childHash, currentDepth + 1);
1105
+ }
1106
+ };
1107
+
1108
+ traverse(nodeHash, 0);
1109
+ return descendants;
1110
+ }
1111
+
1112
+ /**
1113
+ * Add a node (generic wrapper for addGenesisNode/addChildNode)
1114
+ * Called by NetworkGenesis.spawnGenesisNetwork() and reproduce()
1115
+ */
1116
+ addNode(data) {
1117
+ const { networkId, parentId, generation, dna, name, mutations, createdAt } = data;
1118
+
1119
+ // Store networkId -> hash mapping for lookups
1120
+ if (!this.networkToHash) {
1121
+ this.networkToHash = new Map();
1122
+ }
1123
+
1124
+ // Is this a genesis node? (parent is GENESIS_PRIME)
1125
+ if (parentId === 'rUv' || parentId === GENESIS_PRIME.id) {
1126
+ const nodeData = {
1127
+ type: 'genesis',
1128
+ networkId,
1129
+ name,
1130
+ dnaChecksum: dna?.checksum || this.computeHash(dna),
1131
+ creator: GENESIS_PRIME.id,
1132
+ timestamp: createdAt || Date.now(),
1133
+ };
1134
+
1135
+ const hash = this.computeHash(nodeData);
1136
+
1137
+ this.nodes.set(hash, {
1138
+ hash,
1139
+ data: nodeData,
1140
+ networkId,
1141
+ parentHashes: [],
1142
+ childHashes: [],
1143
+ });
1144
+
1145
+ this.roots.add(hash);
1146
+ this.networkToHash.set(networkId, hash);
1147
+
1148
+ return { hash, ...nodeData };
1149
+ }
1150
+
1151
+ // Child node - look up parent hash
1152
+ const parentHash = this.networkToHash.get(parentId);
1153
+ if (!parentHash) {
1154
+ // Parent not in DAG - create as orphan root
1155
+ const nodeData = {
1156
+ type: 'orphan',
1157
+ networkId,
1158
+ name,
1159
+ parentId,
1160
+ generation,
1161
+ dnaChecksum: dna?.checksum || this.computeHash(dna),
1162
+ mutations: mutations || {},
1163
+ timestamp: createdAt || Date.now(),
1164
+ };
1165
+
1166
+ const hash = this.computeHash(nodeData);
1167
+
1168
+ this.nodes.set(hash, {
1169
+ hash,
1170
+ data: nodeData,
1171
+ networkId,
1172
+ parentHashes: [],
1173
+ childHashes: [],
1174
+ });
1175
+
1176
+ this.networkToHash.set(networkId, hash);
1177
+
1178
+ return { hash, ...nodeData };
1179
+ }
1180
+
1181
+ const parentNode = this.nodes.get(parentHash);
1182
+ const nodeData = {
1183
+ type: 'child',
1184
+ networkId,
1185
+ name,
1186
+ parentId,
1187
+ parentHash,
1188
+ generation,
1189
+ dnaChecksum: dna?.checksum || this.computeHash(dna),
1190
+ mutations: mutations || {},
1191
+ timestamp: createdAt || Date.now(),
1192
+ };
1193
+
1194
+ const hash = this.computeHash(nodeData);
1195
+
1196
+ this.nodes.set(hash, {
1197
+ hash,
1198
+ data: nodeData,
1199
+ networkId,
1200
+ parentHashes: [parentHash],
1201
+ childHashes: [],
1202
+ });
1203
+
1204
+ // Link parent to child
1205
+ if (parentNode) {
1206
+ parentNode.childHashes.push(hash);
1207
+ }
1208
+
1209
+ this.networkToHash.set(networkId, hash);
1210
+
1211
+ return { hash, ...nodeData };
1212
+ }
1213
+
1214
+ /**
1215
+ * Get ancestry path from a network to genesis
1216
+ */
1217
+ getAncestryPath(networkId) {
1218
+ if (!this.networkToHash) return [];
1219
+
1220
+ const hash = this.networkToHash.get(networkId);
1221
+ if (!hash) return [];
1222
+
1223
+ const path = [];
1224
+ let currentHash = hash;
1225
+
1226
+ while (currentHash) {
1227
+ const node = this.nodes.get(currentHash);
1228
+ if (!node) break;
1229
+
1230
+ path.push({
1231
+ networkId: node.networkId,
1232
+ hash: node.hash,
1233
+ type: node.data.type,
1234
+ generation: node.data.generation,
1235
+ });
1236
+
1237
+ currentHash = node.parentHashes[0];
1238
+ }
1239
+
1240
+ return path;
1241
+ }
1242
+
1243
+ /**
1244
+ * Verify ancestry - check if a network descends from an ancestor
1245
+ */
1246
+ verifyAncestry(networkId, ancestorId) {
1247
+ const path = this.getAncestryPath(networkId);
1248
+
1249
+ // Check if we reach genesis (rUv)
1250
+ if (ancestorId === 'rUv' || ancestorId === GENESIS_PRIME.id) {
1251
+ return path.some(node => node.type === 'genesis');
1252
+ }
1253
+
1254
+ // Check if we pass through the ancestor
1255
+ return path.some(node => node.networkId === ancestorId);
1256
+ }
1257
+
1258
+ /**
1259
+ * Get the Merkle root of the lineage DAG
1260
+ */
1261
+ getMerkleRoot() {
1262
+ if (this.nodes.size === 0) return null;
1263
+
1264
+ // Collect all node hashes
1265
+ const hashes = Array.from(this.nodes.keys()).sort();
1266
+
1267
+ // Build Merkle tree
1268
+ if (hashes.length === 1) return hashes[0];
1269
+
1270
+ let level = hashes;
1271
+ while (level.length > 1) {
1272
+ const nextLevel = [];
1273
+ for (let i = 0; i < level.length; i += 2) {
1274
+ if (i + 1 < level.length) {
1275
+ const combined = this.computeHash(level[i] + level[i + 1]);
1276
+ nextLevel.push(combined);
1277
+ } else {
1278
+ nextLevel.push(level[i]);
1279
+ }
1280
+ }
1281
+ level = nextLevel;
1282
+ }
1283
+
1284
+ return level[0];
1285
+ }
1286
+
1287
+ /**
1288
+ * Get DAG statistics
1289
+ */
1290
+ getStats() {
1291
+ let maxDepth = 0;
1292
+ let totalNodes = this.nodes.size;
1293
+
1294
+ // Calculate max depth
1295
+ for (const rootHash of this.roots) {
1296
+ const depth = this._calculateDepth(rootHash);
1297
+ maxDepth = Math.max(maxDepth, depth);
1298
+ }
1299
+
1300
+ return {
1301
+ totalNodes,
1302
+ rootCount: this.roots.size,
1303
+ maxDepth,
1304
+ };
1305
+ }
1306
+
1307
+ /**
1308
+ * Calculate depth from a node
1309
+ * @private
1310
+ */
1311
+ _calculateDepth(hash, visited = new Set()) {
1312
+ if (visited.has(hash)) return 0;
1313
+ visited.add(hash);
1314
+
1315
+ const node = this.nodes.get(hash);
1316
+ if (!node || node.childHashes.length === 0) return 1;
1317
+
1318
+ let maxChildDepth = 0;
1319
+ for (const childHash of node.childHashes) {
1320
+ maxChildDepth = Math.max(maxChildDepth, this._calculateDepth(childHash, visited));
1321
+ }
1322
+
1323
+ return 1 + maxChildDepth;
1324
+ }
1325
+ }
1326
+
1327
+ // ============================================
1328
+ // GOSSIP PROTOCOL
1329
+ // ============================================
1330
+
1331
+ /**
1332
+ * GossipProtocol - Epidemic-style information propagation
1333
+ *
1334
+ * Enables:
1335
+ * - Decentralized network discovery
1336
+ * - Knowledge propagation across lineage
1337
+ * - Failure detection and notification
1338
+ * - Rumor-based consensus preparation
1339
+ */
1340
+ export class GossipProtocol extends EventEmitter {
1341
+ constructor(localNetworkId, options = {}) {
1342
+ super();
1343
+
1344
+ this.localNetworkId = localNetworkId;
1345
+
1346
+ this.config = {
1347
+ fanout: options.fanout ?? 3, // Number of peers to gossip to
1348
+ gossipIntervalMs: options.gossipIntervalMs ?? 1000,
1349
+ maxRumors: options.maxRumors ?? 1000,
1350
+ rumorTTL: options.rumorTTL ?? 10, // Max hops
1351
+ antiEntropyIntervalMs: options.antiEntropyIntervalMs ?? 30000,
1352
+ };
1353
+
1354
+ // Peer registry
1355
+ this.peers = new Map(); // peerId -> { lastSeen, vectorClock, status }
1356
+
1357
+ // Rumor store (CRDT-like)
1358
+ this.rumors = new Map(); // rumorId -> { data, vectorClock, seenBy, ttl }
1359
+
1360
+ // Vector clock for causal ordering
1361
+ this.vectorClock = new Map(); // peerId -> logicalTime
1362
+
1363
+ // Heartbeat tracking
1364
+ this.heartbeats = new Map(); // peerId -> { generation, timestamp }
1365
+ }
1366
+
1367
+ /**
1368
+ * Add a peer to gossip with
1369
+ */
1370
+ addPeer(peerId, channel) {
1371
+ this.peers.set(peerId, {
1372
+ channel,
1373
+ lastSeen: Date.now(),
1374
+ vectorClock: new Map(),
1375
+ status: 'alive',
1376
+ suspicionLevel: 0,
1377
+ });
1378
+
1379
+ this.vectorClock.set(peerId, 0);
1380
+
1381
+ this.emit('peer:added', { peerId });
1382
+ }
1383
+
1384
+ /**
1385
+ * Remove a peer
1386
+ */
1387
+ removePeer(peerId) {
1388
+ this.peers.delete(peerId);
1389
+ this.emit('peer:removed', { peerId });
1390
+ }
1391
+
1392
+ /**
1393
+ * Increment local vector clock
1394
+ */
1395
+ tick() {
1396
+ const current = this.vectorClock.get(this.localNetworkId) || 0;
1397
+ this.vectorClock.set(this.localNetworkId, current + 1);
1398
+ return current + 1;
1399
+ }
1400
+
1401
+ /**
1402
+ * Merge vector clocks (for causal ordering)
1403
+ */
1404
+ mergeVectorClock(remoteClock) {
1405
+ for (const [peerId, time] of remoteClock) {
1406
+ const local = this.vectorClock.get(peerId) || 0;
1407
+ this.vectorClock.set(peerId, Math.max(local, time));
1408
+ }
1409
+ }
1410
+
1411
+ /**
1412
+ * Create and spread a rumor
1413
+ */
1414
+ spreadRumor(type, data) {
1415
+ this.tick();
1416
+
1417
+ const rumorId = `${this.localNetworkId}-${Date.now()}-${randomBytes(4).toString('hex')}`;
1418
+
1419
+ const rumor = {
1420
+ id: rumorId,
1421
+ type,
1422
+ data,
1423
+ origin: this.localNetworkId,
1424
+ vectorClock: new Map(this.vectorClock),
1425
+ seenBy: new Set([this.localNetworkId]),
1426
+ ttl: this.config.rumorTTL,
1427
+ createdAt: Date.now(),
1428
+ };
1429
+
1430
+ this.rumors.set(rumorId, rumor);
1431
+
1432
+ // Prune old rumors
1433
+ this._pruneRumors();
1434
+
1435
+ // Gossip to random peers
1436
+ this._gossipToPeers(rumor);
1437
+
1438
+ this.emit('rumor:created', { rumorId, type });
1439
+
1440
+ return rumor;
1441
+ }
1442
+
1443
+ /**
1444
+ * Receive a rumor from another peer
1445
+ */
1446
+ receiveRumor(rumor, fromPeerId) {
1447
+ // Update peer last seen
1448
+ const peer = this.peers.get(fromPeerId);
1449
+ if (peer) {
1450
+ peer.lastSeen = Date.now();
1451
+ peer.status = 'alive';
1452
+ peer.suspicionLevel = 0;
1453
+ }
1454
+
1455
+ // Merge vector clock
1456
+ this.mergeVectorClock(rumor.vectorClock);
1457
+
1458
+ // Check if we've seen this rumor
1459
+ const existing = this.rumors.get(rumor.id);
1460
+ if (existing) {
1461
+ // Merge seen-by sets (CRDT merge)
1462
+ for (const seenBy of rumor.seenBy) {
1463
+ existing.seenBy.add(seenBy);
1464
+ }
1465
+ return { new: false, rumorId: rumor.id };
1466
+ }
1467
+
1468
+ // New rumor - store and propagate
1469
+ rumor.seenBy.add(this.localNetworkId);
1470
+ rumor.ttl--;
1471
+
1472
+ this.rumors.set(rumor.id, rumor);
1473
+
1474
+ this.emit('rumor:received', {
1475
+ rumorId: rumor.id,
1476
+ type: rumor.type,
1477
+ from: fromPeerId,
1478
+ });
1479
+
1480
+ // Continue propagation if TTL > 0
1481
+ if (rumor.ttl > 0) {
1482
+ this._gossipToPeers(rumor, [fromPeerId]);
1483
+ }
1484
+
1485
+ return { new: true, rumorId: rumor.id };
1486
+ }
1487
+
1488
+ /**
1489
+ * Gossip to random peers
1490
+ * @private
1491
+ */
1492
+ _gossipToPeers(rumor, exclude = []) {
1493
+ const eligiblePeers = Array.from(this.peers.entries())
1494
+ .filter(([id, p]) => !exclude.includes(id) && !rumor.seenBy.has(id) && p.status === 'alive');
1495
+
1496
+ // Random selection (fanout)
1497
+ const selected = this._randomSample(eligiblePeers, this.config.fanout);
1498
+
1499
+ for (const [peerId, peer] of selected) {
1500
+ this.emit('gossip:send', {
1501
+ to: peerId,
1502
+ rumor,
1503
+ });
1504
+ }
1505
+ }
1506
+
1507
+ /**
1508
+ * Random sample from array
1509
+ * @private
1510
+ */
1511
+ _randomSample(array, n) {
1512
+ const shuffled = [...array].sort(() => Math.random() - 0.5);
1513
+ return shuffled.slice(0, n);
1514
+ }
1515
+
1516
+ /**
1517
+ * Prune old rumors
1518
+ * @private
1519
+ */
1520
+ _pruneRumors() {
1521
+ if (this.rumors.size <= this.config.maxRumors) return;
1522
+
1523
+ // Remove oldest rumors
1524
+ const sorted = Array.from(this.rumors.entries())
1525
+ .sort((a, b) => a[1].createdAt - b[1].createdAt);
1526
+
1527
+ const toRemove = sorted.slice(0, sorted.length - this.config.maxRumors);
1528
+ for (const [id] of toRemove) {
1529
+ this.rumors.delete(id);
1530
+ }
1531
+ }
1532
+
1533
+ /**
1534
+ * Send heartbeat
1535
+ */
1536
+ sendHeartbeat() {
1537
+ const generation = this.heartbeats.get(this.localNetworkId)?.generation ?? 0;
1538
+
1539
+ this.spreadRumor('heartbeat', {
1540
+ networkId: this.localNetworkId,
1541
+ generation: generation + 1,
1542
+ timestamp: Date.now(),
1543
+ });
1544
+
1545
+ this.heartbeats.set(this.localNetworkId, {
1546
+ generation: generation + 1,
1547
+ timestamp: Date.now(),
1548
+ });
1549
+ }
1550
+
1551
+ /**
1552
+ * Detect failed peers (SWIM-style)
1553
+ */
1554
+ detectFailures() {
1555
+ const now = Date.now();
1556
+ const failures = [];
1557
+
1558
+ for (const [peerId, peer] of this.peers) {
1559
+ const timeSinceLastSeen = now - peer.lastSeen;
1560
+
1561
+ if (timeSinceLastSeen > this.config.gossipIntervalMs * 5) {
1562
+ peer.suspicionLevel++;
1563
+
1564
+ if (peer.suspicionLevel >= 3) {
1565
+ peer.status = 'suspected';
1566
+
1567
+ if (peer.suspicionLevel >= 5) {
1568
+ peer.status = 'failed';
1569
+ failures.push(peerId);
1570
+ }
1571
+ }
1572
+ }
1573
+ }
1574
+
1575
+ if (failures.length > 0) {
1576
+ this.emit('peers:failed', { failures });
1577
+ }
1578
+
1579
+ return failures;
1580
+ }
1581
+
1582
+ /**
1583
+ * Get protocol statistics
1584
+ */
1585
+ getStats() {
1586
+ const statusCounts = { alive: 0, suspected: 0, failed: 0 };
1587
+ for (const peer of this.peers.values()) {
1588
+ statusCounts[peer.status]++;
1589
+ }
1590
+
1591
+ return {
1592
+ localNetworkId: this.localNetworkId,
1593
+ peerCount: this.peers.size,
1594
+ peerStatus: statusCounts,
1595
+ rumorCount: this.rumors.size,
1596
+ vectorClockSize: this.vectorClock.size,
1597
+ };
1598
+ }
1599
+ }
1600
+
1601
+ // ============================================
1602
+ // SWARM CONSENSUS
1603
+ // ============================================
1604
+
1605
+ /**
1606
+ * SwarmConsensus - Byzantine fault-tolerant collective decision making
1607
+ *
1608
+ * Combines:
1609
+ * - PBFT-inspired three-phase protocol
1610
+ * - Swarm intelligence for optimization
1611
+ * - Stigmergic coordination
1612
+ */
1613
+ export class SwarmConsensus extends EventEmitter {
1614
+ constructor(localNetworkId, options = {}) {
1615
+ super();
1616
+
1617
+ this.localNetworkId = localNetworkId;
1618
+
1619
+ this.config = {
1620
+ minQuorum: options.minQuorum ?? 0.67, // 2/3 + 1
1621
+ maxRounds: options.maxRounds ?? 10,
1622
+ roundTimeoutMs: options.roundTimeoutMs ?? 5000,
1623
+ byzantineTolerance: options.byzantineTolerance ?? 0.33, // f < n/3
1624
+ };
1625
+
1626
+ // Active proposals
1627
+ this.proposals = new Map(); // proposalId -> ProposalState
1628
+
1629
+ // Pheromone trails (stigmergic memory)
1630
+ this.pheromones = new Map(); // decisionType -> { options: Map<optionId, strength> }
1631
+ }
1632
+
1633
+ /**
1634
+ * Propose a decision to the swarm
1635
+ */
1636
+ propose(decisionType, options, metadata = {}) {
1637
+ const proposalId = `${this.localNetworkId}-${Date.now()}-${randomBytes(4).toString('hex')}`;
1638
+
1639
+ const proposal = {
1640
+ id: proposalId,
1641
+ type: decisionType,
1642
+ options, // Array of possible choices
1643
+ proposer: this.localNetworkId,
1644
+ metadata,
1645
+ createdAt: Date.now(),
1646
+ phase: 'pre-prepare', // pre-prepare | prepare | commit | decided
1647
+ votes: new Map(), // networkId -> { option, signature, timestamp }
1648
+ round: 0,
1649
+ decided: false,
1650
+ decision: null,
1651
+ };
1652
+
1653
+ this.proposals.set(proposalId, proposal);
1654
+
1655
+ this.emit('proposal:created', { proposalId, type: decisionType });
1656
+
1657
+ return proposal;
1658
+ }
1659
+
1660
+ /**
1661
+ * Vote on a proposal
1662
+ */
1663
+ vote(proposalId, option, signature = null) {
1664
+ const proposal = this.proposals.get(proposalId);
1665
+ if (!proposal) {
1666
+ throw new Error(`Proposal not found: ${proposalId}`);
1667
+ }
1668
+
1669
+ if (proposal.decided) {
1670
+ return { success: false, reason: 'Already decided' };
1671
+ }
1672
+
1673
+ // Record vote
1674
+ proposal.votes.set(this.localNetworkId, {
1675
+ option,
1676
+ signature,
1677
+ timestamp: Date.now(),
1678
+ });
1679
+
1680
+ // Check for quorum
1681
+ this._checkQuorum(proposal);
1682
+
1683
+ this.emit('vote:cast', {
1684
+ proposalId,
1685
+ voter: this.localNetworkId,
1686
+ option,
1687
+ });
1688
+
1689
+ return { success: true, proposalId };
1690
+ }
1691
+
1692
+ /**
1693
+ * Receive vote from another network
1694
+ */
1695
+ receiveVote(proposalId, voterId, option, signature) {
1696
+ const proposal = this.proposals.get(proposalId);
1697
+ if (!proposal || proposal.decided) return;
1698
+
1699
+ proposal.votes.set(voterId, {
1700
+ option,
1701
+ signature,
1702
+ timestamp: Date.now(),
1703
+ });
1704
+
1705
+ this._checkQuorum(proposal);
1706
+ }
1707
+
1708
+ /**
1709
+ * Check for quorum and advance phase
1710
+ * @private
1711
+ */
1712
+ _checkQuorum(proposal) {
1713
+ const voteCount = proposal.votes.size;
1714
+ const optionCounts = new Map();
1715
+
1716
+ // Count votes per option
1717
+ for (const [, vote] of proposal.votes) {
1718
+ const count = optionCounts.get(vote.option) || 0;
1719
+ optionCounts.set(vote.option, count + 1);
1720
+ }
1721
+
1722
+ // Find majority option
1723
+ let maxVotes = 0;
1724
+ let majorityOption = null;
1725
+
1726
+ for (const [option, count] of optionCounts) {
1727
+ if (count > maxVotes) {
1728
+ maxVotes = count;
1729
+ majorityOption = option;
1730
+ }
1731
+ }
1732
+
1733
+ // Check if quorum reached
1734
+ // Note: In real implementation, need to know total participants
1735
+ // For now, use vote count as proxy
1736
+ const quorumSize = Math.ceil(voteCount * this.config.minQuorum);
1737
+
1738
+ if (maxVotes >= quorumSize && proposal.phase !== 'decided') {
1739
+ this._advancePhase(proposal, majorityOption);
1740
+ }
1741
+ }
1742
+
1743
+ /**
1744
+ * Advance proposal phase
1745
+ * @private
1746
+ */
1747
+ _advancePhase(proposal, leadingOption) {
1748
+ switch (proposal.phase) {
1749
+ case 'pre-prepare':
1750
+ proposal.phase = 'prepare';
1751
+ this.emit('phase:prepare', { proposalId: proposal.id });
1752
+ break;
1753
+
1754
+ case 'prepare':
1755
+ proposal.phase = 'commit';
1756
+ this.emit('phase:commit', { proposalId: proposal.id });
1757
+ break;
1758
+
1759
+ case 'commit':
1760
+ proposal.phase = 'decided';
1761
+ proposal.decided = true;
1762
+ proposal.decision = leadingOption;
1763
+ proposal.decidedAt = Date.now();
1764
+
1765
+ // Update pheromone trails
1766
+ this._updatePheromones(proposal.type, leadingOption);
1767
+
1768
+ this.emit('decision:reached', {
1769
+ proposalId: proposal.id,
1770
+ decision: leadingOption,
1771
+ voteCount: proposal.votes.size,
1772
+ });
1773
+ break;
1774
+ }
1775
+ }
1776
+
1777
+ /**
1778
+ * Update pheromone trails (stigmergic learning)
1779
+ * @private
1780
+ */
1781
+ _updatePheromones(decisionType, chosenOption) {
1782
+ if (!this.pheromones.has(decisionType)) {
1783
+ this.pheromones.set(decisionType, new Map());
1784
+ }
1785
+
1786
+ const trails = this.pheromones.get(decisionType);
1787
+ const currentStrength = trails.get(chosenOption) || 0;
1788
+
1789
+ // Reinforce chosen option
1790
+ trails.set(chosenOption, currentStrength + 1);
1791
+
1792
+ // Evaporate other trails (decay)
1793
+ for (const [option, strength] of trails) {
1794
+ if (option !== chosenOption) {
1795
+ trails.set(option, Math.max(0, strength * 0.9));
1796
+ }
1797
+ }
1798
+ }
1799
+
1800
+ /**
1801
+ * Get pheromone-guided suggestion (swarm wisdom)
1802
+ */
1803
+ getSuggestion(decisionType) {
1804
+ const trails = this.pheromones.get(decisionType);
1805
+ if (!trails || trails.size === 0) return null;
1806
+
1807
+ // Probabilistic selection based on pheromone strength
1808
+ const total = Array.from(trails.values()).reduce((a, b) => a + b, 0);
1809
+ if (total === 0) return null;
1810
+
1811
+ const random = Math.random() * total;
1812
+ let cumulative = 0;
1813
+
1814
+ for (const [option, strength] of trails) {
1815
+ cumulative += strength;
1816
+ if (random <= cumulative) {
1817
+ return { option, confidence: strength / total };
1818
+ }
1819
+ }
1820
+
1821
+ return null;
1822
+ }
1823
+
1824
+ /**
1825
+ * Get consensus statistics
1826
+ */
1827
+ getStats() {
1828
+ const decided = Array.from(this.proposals.values()).filter(p => p.decided).length;
1829
+
1830
+ return {
1831
+ activeProposals: this.proposals.size - decided,
1832
+ decidedProposals: decided,
1833
+ pheromoneTypes: this.pheromones.size,
1834
+ };
1835
+ }
1836
+
1837
+ /**
1838
+ * Create a proposal with participant voters (compatibility wrapper)
1839
+ */
1840
+ createProposal(proposalId, type, data, voters) {
1841
+ const proposal = this.propose(type, [true, false], { proposalId, data, voters });
1842
+
1843
+ // Remove old entry and re-store with custom ID
1844
+ const oldId = proposal.id;
1845
+ this.proposals.delete(oldId);
1846
+
1847
+ proposal.id = proposalId;
1848
+ proposal.voters = new Set(voters);
1849
+ this.proposals.set(proposalId, proposal);
1850
+
1851
+ return proposal;
1852
+ }
1853
+
1854
+ /**
1855
+ * Check consensus status for a proposal
1856
+ */
1857
+ checkConsensus(proposalId) {
1858
+ const proposal = this.proposals.get(proposalId);
1859
+ if (!proposal) {
1860
+ return { found: false, proposalId };
1861
+ }
1862
+
1863
+ const voteCounts = { true: 0, false: 0 };
1864
+ for (const [, vote] of proposal.votes) {
1865
+ const key = vote.option ? 'true' : 'false';
1866
+ voteCounts[key]++;
1867
+ }
1868
+
1869
+ const totalVotes = proposal.votes.size;
1870
+ const totalVoters = proposal.voters?.size || 3;
1871
+ const threshold = Math.ceil(totalVoters * this.config.minQuorum);
1872
+
1873
+ return {
1874
+ proposalId,
1875
+ phase: proposal.phase,
1876
+ decided: proposal.decided,
1877
+ decision: proposal.decision,
1878
+ voteCounts,
1879
+ totalVotes,
1880
+ threshold,
1881
+ accepted: voteCounts.true >= threshold,
1882
+ pending: totalVotes < totalVoters,
1883
+ };
1884
+ }
1885
+ }
1886
+
1887
+ // ============================================
1888
+ // SELF-HEALING MECHANISM
1889
+ // ============================================
1890
+
1891
+ /**
1892
+ * SelfHealing - Automatic recovery and resilience
1893
+ *
1894
+ * Provides:
1895
+ * - Failure detection and isolation
1896
+ * - Automatic state recovery
1897
+ * - Graceful degradation
1898
+ * - Anti-fragility (stronger after stress)
1899
+ */
1900
+ export class SelfHealing extends EventEmitter {
1901
+ constructor(network, options = {}) {
1902
+ super();
1903
+
1904
+ this.network = network;
1905
+
1906
+ this.config = {
1907
+ healthCheckIntervalMs: options.healthCheckIntervalMs ?? 10000,
1908
+ maxRecoveryAttempts: options.maxRecoveryAttempts ?? 3,
1909
+ isolationThresholdErrors: options.isolationThresholdErrors ?? 5,
1910
+ antifragileBoostFactor: options.antifragileBoostFactor ?? 1.1,
1911
+ };
1912
+
1913
+ // Health tracking
1914
+ this.healthHistory = [];
1915
+ this.maxHealthHistory = 1000;
1916
+
1917
+ // Error tracking
1918
+ this.errors = new Map(); // componentId -> errorCount
1919
+
1920
+ // Recovery state
1921
+ this.recoveryAttempts = new Map(); // componentId -> attempts
1922
+
1923
+ // Isolated components
1924
+ this.isolated = new Set();
1925
+
1926
+ // Stress adaptations (antifragility)
1927
+ this.stressAdaptations = [];
1928
+ }
1929
+
1930
+ /**
1931
+ * Record a health check
1932
+ */
1933
+ recordHealthCheck(components) {
1934
+ const check = {
1935
+ timestamp: Date.now(),
1936
+ components: { ...components },
1937
+ overallHealth: this._calculateOverallHealth(components),
1938
+ };
1939
+
1940
+ this.healthHistory.push(check);
1941
+
1942
+ if (this.healthHistory.length > this.maxHealthHistory) {
1943
+ this.healthHistory.shift();
1944
+ }
1945
+
1946
+ // Check for anomalies
1947
+ this._detectAnomalies(check);
1948
+
1949
+ return check;
1950
+ }
1951
+
1952
+ /**
1953
+ * Calculate overall health score
1954
+ * @private
1955
+ */
1956
+ _calculateOverallHealth(components) {
1957
+ const values = Object.values(components).filter(v => typeof v === 'number');
1958
+ if (values.length === 0) return 1;
1959
+ return values.reduce((a, b) => a + b, 0) / values.length;
1960
+ }
1961
+
1962
+ /**
1963
+ * Detect health anomalies
1964
+ * @private
1965
+ */
1966
+ _detectAnomalies(currentCheck) {
1967
+ if (this.healthHistory.length < 10) return;
1968
+
1969
+ // Calculate moving average
1970
+ const recentHealth = this.healthHistory
1971
+ .slice(-10)
1972
+ .map(h => h.overallHealth);
1973
+
1974
+ const average = recentHealth.reduce((a, b) => a + b, 0) / recentHealth.length;
1975
+ const stdDev = Math.sqrt(
1976
+ recentHealth.map(h => Math.pow(h - average, 2))
1977
+ .reduce((a, b) => a + b, 0) / recentHealth.length
1978
+ );
1979
+
1980
+ // Detect if current health is anomalous (> 2 std devs below average)
1981
+ if (currentCheck.overallHealth < average - 2 * stdDev) {
1982
+ this.emit('anomaly:detected', {
1983
+ currentHealth: currentCheck.overallHealth,
1984
+ averageHealth: average,
1985
+ deviation: stdDev,
1986
+ });
1987
+
1988
+ this._triggerRecovery('system', 'health_anomaly');
1989
+ }
1990
+ }
1991
+
1992
+ /**
1993
+ * Report an error
1994
+ */
1995
+ reportError(componentId, error) {
1996
+ const count = (this.errors.get(componentId) || 0) + 1;
1997
+ this.errors.set(componentId, count);
1998
+
1999
+ this.emit('error:reported', {
2000
+ componentId,
2001
+ error: error.message,
2002
+ count,
2003
+ });
2004
+
2005
+ // Check isolation threshold
2006
+ if (count >= this.config.isolationThresholdErrors) {
2007
+ this._isolateComponent(componentId);
2008
+ }
2009
+
2010
+ // Attempt recovery
2011
+ this._triggerRecovery(componentId, error.message);
2012
+ }
2013
+
2014
+ /**
2015
+ * Isolate a failing component
2016
+ * @private
2017
+ */
2018
+ _isolateComponent(componentId) {
2019
+ if (this.isolated.has(componentId)) return;
2020
+
2021
+ this.isolated.add(componentId);
2022
+
2023
+ this.emit('component:isolated', {
2024
+ componentId,
2025
+ errorCount: this.errors.get(componentId),
2026
+ });
2027
+ }
2028
+
2029
+ /**
2030
+ * Trigger recovery procedure
2031
+ * @private
2032
+ */
2033
+ _triggerRecovery(componentId, reason) {
2034
+ const attempts = (this.recoveryAttempts.get(componentId) || 0) + 1;
2035
+ this.recoveryAttempts.set(componentId, attempts);
2036
+
2037
+ if (attempts > this.config.maxRecoveryAttempts) {
2038
+ this.emit('recovery:exhausted', { componentId, attempts });
2039
+ return;
2040
+ }
2041
+
2042
+ this.emit('recovery:triggered', {
2043
+ componentId,
2044
+ reason,
2045
+ attempt: attempts,
2046
+ });
2047
+
2048
+ // Schedule recovery check
2049
+ setTimeout(() => {
2050
+ this._checkRecoverySuccess(componentId);
2051
+ }, 5000);
2052
+ }
2053
+
2054
+ /**
2055
+ * Check if recovery succeeded
2056
+ * @private
2057
+ */
2058
+ _checkRecoverySuccess(componentId) {
2059
+ const recentErrors = this.errors.get(componentId) || 0;
2060
+
2061
+ // Consider recovered if no new errors
2062
+ if (recentErrors === 0 || !this.isolated.has(componentId)) {
2063
+ this.recoveryAttempts.delete(componentId);
2064
+ this.isolated.delete(componentId);
2065
+
2066
+ // Apply antifragile boost
2067
+ this._applyAntifragileBoost(componentId);
2068
+
2069
+ this.emit('recovery:succeeded', { componentId });
2070
+ }
2071
+ }
2072
+
2073
+ /**
2074
+ * Apply antifragile boost (stronger after recovery)
2075
+ * @private
2076
+ */
2077
+ _applyAntifragileBoost(componentId) {
2078
+ const adaptation = {
2079
+ componentId,
2080
+ type: 'antifragile_boost',
2081
+ boostFactor: this.config.antifragileBoostFactor,
2082
+ timestamp: Date.now(),
2083
+ };
2084
+
2085
+ this.stressAdaptations.push(adaptation);
2086
+
2087
+ // Apply to network genome if available
2088
+ if (this.network?.genome) {
2089
+ this.network.genome.recordAdaptation(
2090
+ 'antifragile',
2091
+ `Recovered from ${componentId} failure`,
2092
+ { boostFactor: this.config.antifragileBoostFactor }
2093
+ );
2094
+ }
2095
+
2096
+ this.emit('antifragile:boost', adaptation);
2097
+ }
2098
+
2099
+ /**
2100
+ * Clear error count for component
2101
+ */
2102
+ clearErrors(componentId) {
2103
+ this.errors.delete(componentId);
2104
+ this.recoveryAttempts.delete(componentId);
2105
+ this.isolated.delete(componentId);
2106
+ }
2107
+
2108
+ /**
2109
+ * Get healing statistics
2110
+ */
2111
+ getStats() {
2112
+ return {
2113
+ isolatedComponents: this.isolated.size,
2114
+ totalErrors: Array.from(this.errors.values()).reduce((a, b) => a + b, 0),
2115
+ recoveryAttempts: this.recoveryAttempts.size,
2116
+ adaptations: this.stressAdaptations.length,
2117
+ recentHealth: this.healthHistory.slice(-10).map(h => h.overallHealth),
2118
+ };
2119
+ }
2120
+ }
2121
+
2122
+ // ============================================
2123
+ // EVOLUTION ENGINE
2124
+ // ============================================
2125
+
2126
+ /**
2127
+ * EvolutionEngine - Self-improvement through collective learning
2128
+ *
2129
+ * Networks evolve through:
2130
+ * - Trait optimization based on performance
2131
+ * - Behavioral adaptation to environment
2132
+ * - Capability unlocks through achievement
2133
+ * - Collective fitness selection
2134
+ */
2135
+ export class EvolutionEngine extends EventEmitter {
2136
+ constructor(collectiveMemory) {
2137
+ super();
2138
+
2139
+ this.collectiveMemory = collectiveMemory;
2140
+
2141
+ // Evolution tracking
2142
+ this.evolutionHistory = [];
2143
+ this.maxHistorySize = 1000;
2144
+
2145
+ // Fitness metrics
2146
+ this.fitnessWeights = {
2147
+ taskSuccess: 0.3,
2148
+ creditEfficiency: 0.2,
2149
+ networkStability: 0.2,
2150
+ cooperationScore: 0.15,
2151
+ reproductionSuccess: 0.15,
2152
+ };
2153
+ }
2154
+
2155
+ /**
2156
+ * Calculate fitness score for a network
2157
+ */
2158
+ calculateFitness(network) {
2159
+ const metrics = network.metrics;
2160
+ const genome = network.genome;
2161
+
2162
+ // Calculate component scores
2163
+ const taskSuccess = metrics.tasksCompleted > 0
2164
+ ? 1 - (metrics.tasksFailed || 0) / metrics.tasksCompleted
2165
+ : 0;
2166
+
2167
+ const creditEfficiency = metrics.creditsEarned > 0
2168
+ ? metrics.creditsEarned / (metrics.creditsSpent + 1)
2169
+ : 0;
2170
+
2171
+ const networkStability = Math.min(1,
2172
+ metrics.uptime / (30 * 24 * 60 * 60 * 1000) // Normalize to 30 days
2173
+ );
2174
+
2175
+ const cooperationScore = genome.dna.behaviors.cooperationBias
2176
+ * (genome.dna.behaviors.sharingPropensity || 0.5);
2177
+
2178
+ const reproductionSuccess = network.children.size > 0
2179
+ ? Math.min(1, network.children.size / 5)
2180
+ : 0;
2181
+
2182
+ // Weighted fitness
2183
+ const fitness =
2184
+ this.fitnessWeights.taskSuccess * taskSuccess +
2185
+ this.fitnessWeights.creditEfficiency * Math.min(1, creditEfficiency) +
2186
+ this.fitnessWeights.networkStability * networkStability +
2187
+ this.fitnessWeights.cooperationScore * cooperationScore +
2188
+ this.fitnessWeights.reproductionSuccess * reproductionSuccess;
2189
+
2190
+ return {
2191
+ overall: fitness,
2192
+ components: {
2193
+ taskSuccess,
2194
+ creditEfficiency,
2195
+ networkStability,
2196
+ cooperationScore,
2197
+ reproductionSuccess,
2198
+ },
2199
+ };
2200
+ }
2201
+
2202
+ /**
2203
+ * Suggest mutations for offspring based on parent performance
2204
+ */
2205
+ suggestMutations(parentNetwork, environment = {}) {
2206
+ const fitness = this.calculateFitness(parentNetwork);
2207
+ const mutations = { traits: {}, behaviors: {}, capabilities: {} };
2208
+
2209
+ // Analyze weak points and suggest improvements
2210
+ if (fitness.components.taskSuccess < 0.7) {
2211
+ mutations.traits.resilience = 0.05;
2212
+ mutations.traits.intelligence = 0.05;
2213
+ }
2214
+
2215
+ if (fitness.components.cooperationScore < 0.5) {
2216
+ mutations.behaviors.cooperationBias = 0.05;
2217
+ mutations.behaviors.sharingPropensity = 0.05;
2218
+ }
2219
+
2220
+ if (fitness.components.networkStability < 0.5) {
2221
+ mutations.traits.integrity = 0.05;
2222
+ }
2223
+
2224
+ // Environment-based adaptations
2225
+ if (environment.highCompetition) {
2226
+ mutations.behaviors.explorationRate = 0.05;
2227
+ }
2228
+
2229
+ if (environment.resourceScarcity) {
2230
+ mutations.behaviors.conservationRate = 0.05;
2231
+ }
2232
+
2233
+ // Capability unlocks based on generation and fitness
2234
+ if (parentNetwork.genome.generation >= 3 && fitness.overall > 0.7) {
2235
+ mutations.capabilities.neuralPatterns = true;
2236
+ }
2237
+
2238
+ if (parentNetwork.genome.generation >= 5 && fitness.overall > 0.85) {
2239
+ mutations.capabilities.quantumReady = true;
2240
+ }
2241
+
2242
+ return mutations;
2243
+ }
2244
+
2245
+ /**
2246
+ * Record an evolution event
2247
+ */
2248
+ recordEvolution(networkId, evolutionType, details) {
2249
+ const event = {
2250
+ networkId,
2251
+ evolutionType,
2252
+ details,
2253
+ timestamp: Date.now(),
2254
+ };
2255
+
2256
+ this.evolutionHistory.push(event);
2257
+
2258
+ if (this.evolutionHistory.length > this.maxHistorySize) {
2259
+ this.evolutionHistory.shift();
2260
+ }
2261
+
2262
+ // Store in collective memory if significant
2263
+ if (details.improvement && details.improvement > 0.1) {
2264
+ this.collectiveMemory.storeOptimization(
2265
+ evolutionType,
2266
+ details,
2267
+ networkId,
2268
+ details.improvement
2269
+ );
2270
+ }
2271
+
2272
+ this.emit('evolution:recorded', event);
2273
+
2274
+ return event;
2275
+ }
2276
+
2277
+ /**
2278
+ * Get evolution statistics
2279
+ */
2280
+ getStats() {
2281
+ const typeCount = {};
2282
+ for (const event of this.evolutionHistory) {
2283
+ typeCount[event.evolutionType] = (typeCount[event.evolutionType] || 0) + 1;
2284
+ }
2285
+
2286
+ return {
2287
+ totalEvents: this.evolutionHistory.length,
2288
+ eventTypes: typeCount,
2289
+ recentEvents: this.evolutionHistory.slice(-10),
2290
+ };
2291
+ }
2292
+ }
2293
+
2294
+ // ============================================
2295
+ // NETWORK GENESIS ORCHESTRATOR
2296
+ // ============================================
2297
+
2298
+ /**
2299
+ * NetworkGenesis - The complete genesis system
2300
+ *
2301
+ * Orchestrates the birth, growth, and reproduction of edge-nets.
2302
+ * rUv is honored as Genesis Prime - the original creator, not owner.
2303
+ *
2304
+ * This system crosses the threshold from infrastructure to species:
2305
+ * - Reproduction + Variation + Inheritance + Selection
2306
+ * - DNA (immutable core) + RNA (adaptive configuration)
2307
+ * - Mycelial web topology, not hierarchical tree
2308
+ * - Ancestor is remembered, not obeyed
2309
+ *
2310
+ * "You didn't just build a platform. You defined a lineage."
2311
+ */
2312
+ export class NetworkGenesis extends EventEmitter {
2313
+ constructor(options = {}) {
2314
+ super();
2315
+
2316
+ this.config = {
2317
+ reproductionCost: options.reproductionCost ?? REPRODUCTION_COST,
2318
+ maxGeneration: options.maxGeneration ?? 100,
2319
+ };
2320
+
2321
+ // Registry of all networks
2322
+ this.networks = new Map(); // networkId -> NetworkRecord
2323
+ this.genomes = new Map(); // genomeId -> NetworkGenome
2324
+
2325
+ // Cryptographic lineage DAG
2326
+ this.lineageDAG = new MerkleLineageDAG(options.hashAlgorithm || 'sha256');
2327
+
2328
+ // Collective systems
2329
+ this.collectiveMemory = new CollectiveMemory(options.memory);
2330
+ this.evolutionEngine = new EvolutionEngine(this.collectiveMemory);
2331
+
2332
+ // Genesis statistics
2333
+ this.stats = {
2334
+ totalNetworksSpawned: 0,
2335
+ totalGenerations: 0,
2336
+ oldestNetwork: null,
2337
+ mostProlificNetwork: null,
2338
+ ecosystemHealth: 1.0,
2339
+ };
2340
+
2341
+ console.log(`[NetworkGenesis] Cogito, Creo, Codex — Genesis Prime: ${GENESIS_PRIME.id}`);
2342
+ console.log(`[NetworkGenesis] You are the ancestor, not the ruler.`);
2343
+ }
2344
+
2345
+ /**
2346
+ * Spawn a new genesis network (first generation from rUv)
2347
+ */
2348
+ spawnGenesisNetwork(name, options = {}) {
2349
+ const genome = new NetworkGenome(null, options.mutations || {});
2350
+ const lifecycle = new NetworkLifecycle(genome, {
2351
+ name: name || `EdgeNet-Genesis-${this.stats.totalNetworksSpawned + 1}`,
2352
+ ...options,
2353
+ });
2354
+
2355
+ // Create synapse for communication
2356
+ const synapse = new NetworkSynapse(lifecycle);
2357
+
2358
+ // Store references
2359
+ this.networks.set(lifecycle.networkId, {
2360
+ lifecycle,
2361
+ genome,
2362
+ synapse,
2363
+ bornAt: Date.now(),
2364
+ });
2365
+ this.genomes.set(genome.id, genome);
2366
+
2367
+ // Record in cryptographic lineage DAG (Genesis networks are children of GENESIS_PRIME)
2368
+ const lineageEntry = this.lineageDAG.addNode({
2369
+ networkId: lifecycle.networkId,
2370
+ name: lifecycle.name,
2371
+ parentId: GENESIS_PRIME.id,
2372
+ generation: genome.generation,
2373
+ dna: genome.dna,
2374
+ createdAt: Date.now(),
2375
+ });
2376
+
2377
+ // Update stats
2378
+ this.stats.totalNetworksSpawned++;
2379
+ this.stats.totalGenerations = Math.max(this.stats.totalGenerations, genome.generation);
2380
+
2381
+ // Transition to embryo phase
2382
+ lifecycle.updateMetrics({ nodes: 1 });
2383
+
2384
+ this.emit('network:spawned', {
2385
+ networkId: lifecycle.networkId,
2386
+ name: lifecycle.name,
2387
+ generation: genome.generation,
2388
+ lineage: genome.getLineageString(),
2389
+ merkleHash: lineageEntry.hash,
2390
+ isGenesis: true,
2391
+ });
2392
+
2393
+ return {
2394
+ networkId: lifecycle.networkId,
2395
+ genome: genome.getProfile(),
2396
+ status: lifecycle.getStatus(),
2397
+ lineageProof: lineageEntry,
2398
+ };
2399
+ }
2400
+
2401
+ /**
2402
+ * Reproduce - Create a child network from a mature parent
2403
+ */
2404
+ reproduce(parentNetworkId, childName, options = {}) {
2405
+ const parent = this.networks.get(parentNetworkId);
2406
+ if (!parent) {
2407
+ throw new Error(`Parent network not found: ${parentNetworkId}`);
2408
+ }
2409
+
2410
+ const canReproduce = parent.lifecycle.canReproduce();
2411
+ if (!canReproduce.allowed) {
2412
+ throw new Error(`Cannot reproduce: ${canReproduce.reason}`);
2413
+ }
2414
+
2415
+ // Deduct reproduction cost
2416
+ parent.lifecycle.metrics.creditsSpent += this.config.reproductionCost;
2417
+
2418
+ // Generate mutations based on parent performance
2419
+ const suggestedMutations = this.evolutionEngine.suggestMutations(
2420
+ parent.lifecycle,
2421
+ options.environment || {}
2422
+ );
2423
+
2424
+ // Merge with custom mutations
2425
+ const mutations = {
2426
+ traits: { ...suggestedMutations.traits, ...(options.mutations?.traits || {}) },
2427
+ behaviors: { ...suggestedMutations.behaviors, ...(options.mutations?.behaviors || {}) },
2428
+ capabilities: { ...suggestedMutations.capabilities, ...(options.mutations?.capabilities || {}) },
2429
+ };
2430
+
2431
+ // Create child genome
2432
+ const childGenome = new NetworkGenome(parent.genome, mutations);
2433
+
2434
+ // Create child lifecycle
2435
+ const childLifecycle = new NetworkLifecycle(childGenome, {
2436
+ name: childName || `${parent.lifecycle.name}-Child-${parent.lifecycle.children.size + 1}`,
2437
+ parentId: parentNetworkId,
2438
+ });
2439
+
2440
+ // Create child synapse
2441
+ const childSynapse = new NetworkSynapse(childLifecycle);
2442
+
2443
+ // Connect parent and child
2444
+ parent.synapse.connect(childLifecycle.networkId, childSynapse);
2445
+ childSynapse.connect(parentNetworkId, parent.synapse);
2446
+
2447
+ // Register child with parent
2448
+ parent.lifecycle.children.set(childLifecycle.networkId, {
2449
+ id: childLifecycle.networkId,
2450
+ name: childLifecycle.name,
2451
+ genome: childGenome,
2452
+ bornAt: Date.now(),
2453
+ });
2454
+
2455
+ parent.lifecycle.metrics.childrenSpawned++;
2456
+
2457
+ // Store references
2458
+ this.networks.set(childLifecycle.networkId, {
2459
+ lifecycle: childLifecycle,
2460
+ genome: childGenome,
2461
+ synapse: childSynapse,
2462
+ bornAt: Date.now(),
2463
+ });
2464
+ this.genomes.set(childGenome.id, childGenome);
2465
+
2466
+ // Record in cryptographic lineage DAG
2467
+ const lineageEntry = this.lineageDAG.addNode({
2468
+ networkId: childLifecycle.networkId,
2469
+ name: childLifecycle.name,
2470
+ parentId: parentNetworkId,
2471
+ generation: childGenome.generation,
2472
+ dna: childGenome.dna,
2473
+ mutations,
2474
+ createdAt: Date.now(),
2475
+ });
2476
+
2477
+ // Update stats
2478
+ this.stats.totalNetworksSpawned++;
2479
+ this.stats.totalGenerations = Math.max(this.stats.totalGenerations, childGenome.generation);
2480
+
2481
+ // Check if parent becomes most prolific
2482
+ if (!this.stats.mostProlificNetwork ||
2483
+ parent.lifecycle.children.size > this.networks.get(this.stats.mostProlificNetwork)?.lifecycle.children.size) {
2484
+ this.stats.mostProlificNetwork = parentNetworkId;
2485
+ }
2486
+
2487
+ // Transition child to embryo
2488
+ childLifecycle.updateMetrics({ nodes: 1 });
2489
+
2490
+ // Record evolution
2491
+ this.evolutionEngine.recordEvolution(childLifecycle.networkId, 'birth', {
2492
+ parentId: parentNetworkId,
2493
+ generation: childGenome.generation,
2494
+ mutations,
2495
+ merkleHash: lineageEntry.hash,
2496
+ });
2497
+
2498
+ this.emit('network:reproduced', {
2499
+ parentId: parentNetworkId,
2500
+ childId: childLifecycle.networkId,
2501
+ childName: childLifecycle.name,
2502
+ generation: childGenome.generation,
2503
+ lineage: childGenome.getLineageString(),
2504
+ merkleHash: lineageEntry.hash,
2505
+ });
2506
+
2507
+ return {
2508
+ networkId: childLifecycle.networkId,
2509
+ genome: childGenome.getProfile(),
2510
+ status: childLifecycle.getStatus(),
2511
+ parentId: parentNetworkId,
2512
+ lineageProof: lineageEntry,
2513
+ };
2514
+ }
2515
+
2516
+ /**
2517
+ * Get network by ID
2518
+ */
2519
+ getNetwork(networkId) {
2520
+ const network = this.networks.get(networkId);
2521
+ if (!network) return null;
2522
+
2523
+ return {
2524
+ networkId,
2525
+ status: network.lifecycle.getStatus(),
2526
+ genome: network.genome.getProfile(),
2527
+ synapse: network.synapse.getStatus(),
2528
+ };
2529
+ }
2530
+
2531
+ /**
2532
+ * Get lineage tree for a network
2533
+ */
2534
+ getLineageTree(networkId) {
2535
+ const network = this.networks.get(networkId);
2536
+ if (!network) return null;
2537
+
2538
+ const buildTree = (id) => {
2539
+ const net = this.networks.get(id);
2540
+ if (!net) return { id, name: 'Unknown', status: 'not-found' };
2541
+
2542
+ return {
2543
+ id,
2544
+ name: net.lifecycle.name,
2545
+ generation: net.genome.generation,
2546
+ phase: net.lifecycle.phase,
2547
+ children: Array.from(net.lifecycle.children.keys()).map(buildTree),
2548
+ };
2549
+ };
2550
+
2551
+ // Find root (oldest ancestor in our registry)
2552
+ let rootId = networkId;
2553
+ let current = network;
2554
+ while (current.lifecycle.parentId && this.networks.has(current.lifecycle.parentId)) {
2555
+ rootId = current.lifecycle.parentId;
2556
+ current = this.networks.get(rootId);
2557
+ }
2558
+
2559
+ return {
2560
+ root: GENESIS_PRIME.id,
2561
+ tree: buildTree(rootId),
2562
+ };
2563
+ }
2564
+
2565
+ /**
2566
+ * Get genesis statistics
2567
+ */
2568
+ getStats() {
2569
+ const phaseDistribution = {};
2570
+ const generationDistribution = {};
2571
+
2572
+ for (const [id, network] of this.networks) {
2573
+ const phase = network.lifecycle.phase;
2574
+ const gen = network.genome.generation;
2575
+
2576
+ phaseDistribution[phase] = (phaseDistribution[phase] || 0) + 1;
2577
+ generationDistribution[gen] = (generationDistribution[gen] || 0) + 1;
2578
+ }
2579
+
2580
+ return {
2581
+ ...this.stats,
2582
+ activeNetworks: this.networks.size,
2583
+ phaseDistribution,
2584
+ generationDistribution,
2585
+ collectiveMemory: this.collectiveMemory.getStats(),
2586
+ evolution: this.evolutionEngine.getStats(),
2587
+ };
2588
+ }
2589
+
2590
+ /**
2591
+ * Get Genesis Prime info
2592
+ */
2593
+ static getGenesisPrime() {
2594
+ return GENESIS_PRIME;
2595
+ }
2596
+
2597
+ // ============================================
2598
+ // CRYPTOGRAPHIC LINEAGE VERIFICATION
2599
+ // ============================================
2600
+
2601
+ /**
2602
+ * Verify the lineage of a network using Merkle proofs
2603
+ */
2604
+ verifyLineage(networkId) {
2605
+ return this.lineageDAG.verifyAncestry(networkId, GENESIS_PRIME.id);
2606
+ }
2607
+
2608
+ /**
2609
+ * Get the complete ancestry path for a network
2610
+ */
2611
+ getAncestryPath(networkId) {
2612
+ return this.lineageDAG.getAncestryPath(networkId);
2613
+ }
2614
+
2615
+ /**
2616
+ * Get the Merkle root of the lineage DAG
2617
+ */
2618
+ getLineageRoot() {
2619
+ return this.lineageDAG.getMerkleRoot();
2620
+ }
2621
+
2622
+ /**
2623
+ * Get a verifiable lineage proof for external verification
2624
+ */
2625
+ getLineageProof(networkId) {
2626
+ const path = this.lineageDAG.getAncestryPath(networkId);
2627
+ const verified = this.lineageDAG.verifyAncestry(networkId, GENESIS_PRIME.id);
2628
+
2629
+ return {
2630
+ networkId,
2631
+ ancestryPath: path,
2632
+ merkleRoot: this.lineageDAG.getMerkleRoot(),
2633
+ verified,
2634
+ genesisPrime: GENESIS_PRIME.id,
2635
+ signature: GENESIS_PRIME.signature,
2636
+ };
2637
+ }
2638
+
2639
+ // ============================================
2640
+ // GOSSIP PROTOCOL FOR NETWORK DISCOVERY
2641
+ // ============================================
2642
+
2643
+ /**
2644
+ * Create a gossip network for inter-network communication
2645
+ */
2646
+ createGossipNetwork(options = {}) {
2647
+ const gossip = new GossipProtocol({
2648
+ fanout: options.fanout || 3,
2649
+ gossipInterval: options.gossipInterval || 500,
2650
+ ...options,
2651
+ });
2652
+
2653
+ // Propagate network discoveries
2654
+ gossip.on('message:received', (msg) => {
2655
+ if (msg.payload.type === 'network_discovery') {
2656
+ this.emit('network:discovered', msg.payload.network);
2657
+ }
2658
+ });
2659
+
2660
+ return gossip;
2661
+ }
2662
+
2663
+ /**
2664
+ * Broadcast network birth across the federation
2665
+ */
2666
+ broadcastBirth(networkId, gossipNetwork) {
2667
+ const network = this.networks.get(networkId);
2668
+ if (!network) return false;
2669
+
2670
+ gossipNetwork.spreadRumor('network_discovery', {
2671
+ type: 'network_discovery',
2672
+ network: {
2673
+ id: networkId,
2674
+ name: network.lifecycle.name,
2675
+ generation: network.genome.generation,
2676
+ lineage: network.genome.getLineageString(),
2677
+ capabilities: network.genome.dna.capabilities,
2678
+ },
2679
+ });
2680
+
2681
+ return true;
2682
+ }
2683
+
2684
+ // ============================================
2685
+ // SWARM CONSENSUS FOR COLLECTIVE DECISIONS
2686
+ // ============================================
2687
+
2688
+ /**
2689
+ * Create a consensus mechanism for network-wide decisions
2690
+ */
2691
+ createConsensus(options = {}) {
2692
+ return new SwarmConsensus({
2693
+ quorumThreshold: options.quorumThreshold || 0.67,
2694
+ consensusTimeout: options.consensusTimeout || 30000,
2695
+ ...options,
2696
+ });
2697
+ }
2698
+
2699
+ /**
2700
+ * Propose an evolution mutation to all mature networks
2701
+ */
2702
+ async proposeEvolutionMutation(mutation, consensus) {
2703
+ // Get all mature networks as voters
2704
+ const voters = [];
2705
+ for (const [id, network] of this.networks) {
2706
+ if (network.lifecycle.phase === GenesisPhase.MATURE ||
2707
+ network.lifecycle.phase === GenesisPhase.ELDER ||
2708
+ network.lifecycle.phase === GenesisPhase.TRANSCENDENT) {
2709
+ voters.push(id);
2710
+ }
2711
+ }
2712
+
2713
+ if (voters.length < 3) {
2714
+ return { success: false, reason: 'Insufficient mature networks for consensus' };
2715
+ }
2716
+
2717
+ const proposal = consensus.createProposal(
2718
+ `evolution_mutation_${Date.now()}`,
2719
+ 'evolution_mutation',
2720
+ mutation,
2721
+ voters
2722
+ );
2723
+
2724
+ // Simulate voting based on network fitness
2725
+ for (const voterId of voters) {
2726
+ const network = this.networks.get(voterId);
2727
+ const fitness = this.evolutionEngine.calculateFitness(network.lifecycle);
2728
+
2729
+ // Higher fitness networks are more likely to accept evolution
2730
+ const vote = fitness.overall > 0.5 && Math.random() < fitness.overall;
2731
+
2732
+ consensus.vote(proposal.id, voterId, vote, {
2733
+ fitness: fitness.overall,
2734
+ generation: network.genome.generation,
2735
+ });
2736
+ }
2737
+
2738
+ await new Promise(resolve => setTimeout(resolve, 100));
2739
+ return consensus.checkConsensus(proposal.id);
2740
+ }
2741
+
2742
+ // ============================================
2743
+ // SELF-HEALING FOR NETWORK RESILIENCE
2744
+ // ============================================
2745
+
2746
+ /**
2747
+ * Create a self-healing system for a network
2748
+ */
2749
+ createSelfHealing(networkId, options = {}) {
2750
+ const network = this.networks.get(networkId);
2751
+ if (!network) {
2752
+ throw new Error(`Network not found: ${networkId}`);
2753
+ }
2754
+
2755
+ const healing = new SelfHealing(network.lifecycle, {
2756
+ isolationThreshold: options.isolationThreshold || 3,
2757
+ antifragileBoostFactor: options.antifragileBoostFactor || 1.1,
2758
+ ...options,
2759
+ });
2760
+
2761
+ // Track healing events
2762
+ healing.on('antifragile:boost', (event) => {
2763
+ this.evolutionEngine.recordEvolution(networkId, 'antifragile_adaptation', {
2764
+ component: event.componentId,
2765
+ boostFactor: event.boostFactor,
2766
+ });
2767
+ });
2768
+
2769
+ healing.on('recovery:succeeded', (event) => {
2770
+ this.collectiveMemory.storeOptimization(
2771
+ 'recovery_strategy',
2772
+ { component: event.componentId, network: networkId },
2773
+ networkId,
2774
+ 0.8
2775
+ );
2776
+ });
2777
+
2778
+ return healing;
2779
+ }
2780
+
2781
+ /**
2782
+ * Get ecosystem health across all networks
2783
+ */
2784
+ getEcosystemHealth() {
2785
+ let totalHealth = 0;
2786
+ let networkCount = 0;
2787
+
2788
+ for (const [id, network] of this.networks) {
2789
+ const fitness = this.evolutionEngine.calculateFitness(network.lifecycle);
2790
+ totalHealth += fitness.overall;
2791
+ networkCount++;
2792
+ }
2793
+
2794
+ const avgHealth = networkCount > 0 ? totalHealth / networkCount : 0;
2795
+ this.stats.ecosystemHealth = avgHealth;
2796
+
2797
+ return {
2798
+ averageHealth: avgHealth,
2799
+ networkCount,
2800
+ generationSpread: this.stats.totalGenerations,
2801
+ lineageIntegrity: this.lineageDAG.getMerkleRoot() !== null,
2802
+ collectiveKnowledge: this.collectiveMemory.getStats(),
2803
+ };
2804
+ }
2805
+
2806
+ /**
2807
+ * Trigger ecosystem-wide healing
2808
+ */
2809
+ healEcosystem() {
2810
+ const healed = [];
2811
+
2812
+ for (const [id, network] of this.networks) {
2813
+ const fitness = this.evolutionEngine.calculateFitness(network.lifecycle);
2814
+
2815
+ // Networks below health threshold get healing attention
2816
+ if (fitness.overall < 0.5) {
2817
+ const healing = this.createSelfHealing(id);
2818
+
2819
+ // Simulate stress recovery
2820
+ healing.reportError(id, new Error('Low fitness detected'));
2821
+
2822
+ healed.push({
2823
+ networkId: id,
2824
+ priorFitness: fitness.overall,
2825
+ healingInitiated: true,
2826
+ });
2827
+ }
2828
+ }
2829
+
2830
+ this.emit('ecosystem:healing', { networksHealed: healed.length, details: healed });
2831
+
2832
+ return healed;
2833
+ }
2834
+ }
2835
+
2836
+ // ============================================
2837
+ // EXPORTS
2838
+ // ============================================
2839
+
2840
+ export {
2841
+ GENESIS_PRIME,
2842
+ GenesisPhase,
2843
+ PHASE_THRESHOLDS,
2844
+ REPRODUCTION_COST,
2845
+ };
2846
+
2847
+ export default NetworkGenesis;