universal-ai-brain
Version:
🧠 UNIVERSAL AI BRAIN 3.3 - The world's most advanced cognitive architecture with 24 specialized systems, MongoDB 8.1 $rankFusion hybrid search, latest Voyage 3.5 embeddings, and framework-agnostic design. Works with Mastra, Vercel AI, LangChain, OpenAI A
713 lines (663 loc) • 24.1 kB
text/typescript
/**
* @file CausalReasoningEngine.test.ts - Comprehensive tests for causal reasoning system
*
* Tests MongoDB's $graphLookup capabilities for causal reasoning:
* - Recursive causal chain traversal
* - Graph operations for cause-effect relationships
* - Causal inference and learning algorithms
* - Multi-level causal analysis with real MongoDB operations
*/
import { MongoClient, Db } from 'mongodb';
import { CausalReasoningEngine, CausalInferenceRequest, CausalLearningRequest } from '../../intelligence/CausalReasoningEngine';
import { CausalRelationshipCollection } from '../../collections/CausalRelationshipCollection';
import { setupTestDatabase, cleanupTestDatabase, shouldSkipTest } from '../testConfig';
describe('CausalReasoningEngine - Real MongoDB Integration', () => {
let client: MongoClient;
let db: Db;
let causalReasoningEngine: CausalReasoningEngine;
let causalCollection: CausalRelationshipCollection;
beforeAll(async () => {
if (shouldSkipTest()) {
console.log('⏭️ Skipping test: Database not available');
return;
}
try {
const connection = await setupTestDatabase();
client = connection.client;
db = connection.db;
causalReasoningEngine = new CausalReasoningEngine(db);
causalCollection = new CausalRelationshipCollection(db);
await causalReasoningEngine.initialize();
} catch (error) {
console.log('⏭️ Skipping CausalReasoningEngine tests due to setup failure');
console.error('Setup error:', error);
}
});
afterAll(async () => {
if (client) {
await cleanupTestDatabase(client);
}
});
describe('Causal Relationship Storage and Retrieval', () => {
it('should store and retrieve causal relationships with MongoDB', async () => {
if (shouldSkipTest() || !causalCollection || !causalReasoningEngine) return;
const agentId = 'test_agent_causal_001';
// Store a sample causal relationship
const relationshipId = await causalCollection.storeCausalRelationship({
agentId,
timestamp: new Date(),
relationship: {
id: 'rain_wet_ground',
type: 'direct',
category: 'physical',
strength: 0.95,
confidence: 0.9,
cause: {
id: 'rain',
name: 'Rain',
description: 'Precipitation from clouds',
type: 'event',
attributes: { intensity: 'heavy', duration: '2 hours' },
context: {
temporal: { startTime: new Date(), duration: 7200000 },
spatial: { location: 'outdoor', scope: 'local' },
social: { actors: [], stakeholders: [] },
environmental: { temperature: 15, humidity: 0.8 }
}
},
effect: {
id: 'wet_ground',
name: 'Wet Ground',
description: 'Ground becomes wet from rain',
type: 'state',
attributes: { wetness: 'high', coverage: 'complete' },
magnitude: 0.9,
probability: 0.95,
delay: 0,
duration: 3600000
},
mechanism: {
description: 'Water falls from sky and accumulates on ground surface',
steps: [
{
step: 1,
description: 'Rain drops fall from clouds',
type: 'physical',
intermediateState: { raindrops: 'falling' }
},
{
step: 2,
description: 'Water hits ground surface',
type: 'physical',
intermediateState: { impact: 'contact' }
},
{
step: 3,
description: 'Ground absorbs or pools water',
type: 'physical',
intermediateState: { ground: 'wet' }
}
],
conditions: [
{
condition: 'Ground is permeable or has surface area',
required: true,
probability: 1.0
}
],
moderators: [
{
factor: 'ground_type',
effect: 'amplify',
strength: 0.3
}
]
}
},
evidence: {
empirical: {
observations: [
{
id: 'obs_001',
timestamp: new Date(),
observer: 'weather_station',
description: 'Observed rain causing wet ground',
reliability: 0.95,
context: { location: 'test_site' }
}
],
experiments: [],
correlations: [
{
variable1: 'rainfall_amount',
variable2: 'ground_wetness',
coefficient: 0.92,
significance: 0.99,
sampleSize: 100
}
]
},
theoretical: {
theories: [
{
name: 'Gravity and Water Physics',
description: 'Water falls due to gravity and wets surfaces',
support: 1.0,
predictions: ['Water will fall down', 'Surfaces will become wet']
}
],
models: [],
analogies: []
},
counterEvidence: []
},
network: {
parentCauses: [],
childEffects: [
{
effectId: 'muddy_ground',
relationshipType: 'sequential',
strength: 0.7,
directness: 'direct'
}
],
confounders: [],
alternatives: []
},
temporal: {
timing: {
precedence: 'before',
lag: 0,
persistence: 3600000
},
patterns: {
trend: 'stable'
},
history: []
},
inference: {
methods: [
{
method: 'correlation',
result: { strength: 0.95 },
validity: 0.9,
assumptions: ['No confounders', 'Direct causation']
}
],
reasoning: [
{
step: 1,
premise: 'Rain contains water',
conclusion: 'Water will reach ground',
logic: 'deductive',
confidence: 0.99
}
],
uncertainty: {
epistemic: 0.05,
aleatory: 0.02,
model: 0.03,
measurement: 0.01
}
},
learning: {
updates: [],
predictions: [],
performance: {
accuracy: 0.95,
precision: 0.94,
recall: 0.96,
f1Score: 0.95,
calibration: 0.93
}
},
metadata: {
framework: 'causal-reasoning-test',
version: '1.0.0',
source: 'test_data',
reliability: 0.9,
lastValidated: new Date(),
quality: {
completeness: 0.9,
consistency: 0.95,
coherence: 0.9,
plausibility: 0.95
}
}
});
expect(relationshipId).toBeDefined();
// Retrieve the stored relationship
const relationships = await causalCollection.getAgentCausalRelationships(agentId);
expect(relationships).toHaveLength(1);
expect(relationships[0].relationship.cause.name).toBe('Rain');
expect(relationships[0].relationship.effect.name).toBe('Wet Ground');
expect(relationships[0].relationship.strength).toBe(0.95);
});
it('should traverse causal chains using MongoDB $graphLookup', async () => {
if (shouldSkipTest() || !causalCollection || !causalReasoningEngine) return;
const agentId = 'test_agent_causal_002';
// Create a causal chain: A -> B -> C
await causalCollection.storeCausalRelationship({
agentId,
timestamp: new Date(),
relationship: {
id: 'a_causes_b',
type: 'direct',
category: 'logical',
strength: 0.8,
confidence: 0.85,
cause: {
id: 'cause_a',
name: 'Cause A',
description: 'First cause in chain',
type: 'event',
attributes: {},
context: { temporal: {}, spatial: {}, social: {}, environmental: {} }
},
effect: {
id: 'effect_b',
name: 'Effect B',
description: 'Intermediate effect',
type: 'state',
attributes: {},
magnitude: 0.8,
probability: 0.85,
delay: 1000,
duration: 5000
},
mechanism: {
description: 'A causes B through mechanism 1',
steps: [],
conditions: [],
moderators: []
}
},
evidence: {
empirical: { observations: [], experiments: [], correlations: [] },
theoretical: { theories: [], models: [], analogies: [] },
counterEvidence: []
},
network: { parentCauses: [], childEffects: [], confounders: [], alternatives: [] },
temporal: {
timing: { precedence: 'before', lag: 1000, persistence: 5000 },
patterns: { trend: 'stable' },
history: []
},
inference: {
methods: [],
reasoning: [],
uncertainty: { epistemic: 0.1, aleatory: 0.05, model: 0.05, measurement: 0.02 }
},
learning: {
updates: [],
predictions: [],
performance: { accuracy: 0.8, precision: 0.8, recall: 0.8, f1Score: 0.8, calibration: 0.8 }
},
metadata: {
framework: 'test',
version: '1.0.0',
source: 'test',
reliability: 0.8,
lastValidated: new Date(),
quality: { completeness: 0.8, consistency: 0.8, coherence: 0.8, plausibility: 0.8 }
}
});
await causalCollection.storeCausalRelationship({
agentId,
timestamp: new Date(),
relationship: {
id: 'b_causes_c',
type: 'direct',
category: 'logical',
strength: 0.7,
confidence: 0.8,
cause: {
id: 'effect_b',
name: 'Effect B',
description: 'Intermediate cause',
type: 'state',
attributes: {},
context: { temporal: {}, spatial: {}, social: {}, environmental: {} }
},
effect: {
id: 'effect_c',
name: 'Effect C',
description: 'Final effect in chain',
type: 'outcome',
attributes: {},
magnitude: 0.7,
probability: 0.8,
delay: 2000,
duration: 3000
},
mechanism: {
description: 'B causes C through mechanism 2',
steps: [],
conditions: [],
moderators: []
}
},
evidence: {
empirical: { observations: [], experiments: [], correlations: [] },
theoretical: { theories: [], models: [], analogies: [] },
counterEvidence: []
},
network: { parentCauses: [], childEffects: [], confounders: [], alternatives: [] },
temporal: {
timing: { precedence: 'before', lag: 2000, persistence: 3000 },
patterns: { trend: 'stable' },
history: []
},
inference: {
methods: [],
reasoning: [],
uncertainty: { epistemic: 0.15, aleatory: 0.1, model: 0.05, measurement: 0.03 }
},
learning: {
updates: [],
predictions: [],
performance: { accuracy: 0.7, precision: 0.7, recall: 0.7, f1Score: 0.7, calibration: 0.7 }
},
metadata: {
framework: 'test',
version: '1.0.0',
source: 'test',
reliability: 0.7,
lastValidated: new Date(),
quality: { completeness: 0.7, consistency: 0.7, coherence: 0.7, plausibility: 0.7 }
}
});
// Traverse the causal chain using $graphLookup
const causalChains = await causalCollection.traverseCausalChain('cause_a', 'forward', 3);
expect(causalChains.length).toBeGreaterThan(0);
expect(causalChains[0].path).toContain('cause_a');
expect(causalChains[0].totalStrength).toBeGreaterThan(0);
});
});
describe('Causal Inference and Reasoning', () => {
it('should perform causal inference with what-if analysis', async () => {
if (shouldSkipTest() || !causalCollection || !causalReasoningEngine) return;
const agentId = 'test_agent_causal_003';
// Create test data first
await causalCollection.storeCausalRelationship({
agentId,
timestamp: new Date(),
relationship: {
id: 'study_grades',
type: 'direct',
category: 'social',
strength: 0.75,
confidence: 0.8,
cause: {
id: 'study_hours',
name: 'Study Hours',
description: 'Hours spent studying',
type: 'action',
attributes: { hours: 8 },
context: { temporal: {}, spatial: {}, social: {}, environmental: {} }
},
effect: {
id: 'exam_grade',
name: 'Exam Grade',
description: 'Grade received on exam',
type: 'outcome',
attributes: { grade: 'A' },
magnitude: 0.8,
probability: 0.75,
delay: 86400000, // 1 day
duration: 0
},
mechanism: {
description: 'More study time leads to better understanding and higher grades',
steps: [],
conditions: [],
moderators: []
}
},
evidence: {
empirical: { observations: [], experiments: [], correlations: [] },
theoretical: { theories: [], models: [], analogies: [] },
counterEvidence: []
},
network: { parentCauses: [], childEffects: [], confounders: [], alternatives: [] },
temporal: {
timing: { precedence: 'before', lag: 86400000, persistence: 0 },
patterns: { trend: 'increasing' },
history: []
},
inference: {
methods: [],
reasoning: [],
uncertainty: { epistemic: 0.15, aleatory: 0.1, model: 0.1, measurement: 0.05 }
},
learning: {
updates: [],
predictions: [],
performance: { accuracy: 0.75, precision: 0.75, recall: 0.75, f1Score: 0.75, calibration: 0.75 }
},
metadata: {
framework: 'test',
version: '1.0.0',
source: 'test',
reliability: 0.75,
lastValidated: new Date(),
quality: { completeness: 0.8, consistency: 0.8, coherence: 0.8, plausibility: 0.8 }
}
});
const inferenceRequest: CausalInferenceRequest = {
agentId,
scenario: {
description: 'What if student increases study hours?',
context: { subject: 'mathematics', difficulty: 'intermediate' }
},
query: {
type: 'what_if',
cause: 'study_hours',
effect: 'exam_grade',
intervention: { study_hours: 10 }
},
parameters: {
maxDepth: 3,
minStrength: 0.5,
minConfidence: 0.6,
includeIndirect: true
}
};
const result = await causalReasoningEngine.performCausalInference(inferenceRequest);
expect(result).toBeDefined();
expect(result.query.type).toBe('what_if');
expect(result.causalChains).toBeDefined();
expect(result.uncertainty).toBeDefined();
expect(result.recommendations).toBeDefined();
expect(result.metadata.analysisTime).toBeGreaterThan(0);
});
it('should learn causal relationships from observational data', async () => {
if (shouldSkipTest() || !causalCollection || !causalReasoningEngine) return;
const agentId = 'test_agent_causal_004';
const learningRequest: CausalLearningRequest = {
agentId,
observations: [
{
timestamp: new Date('2024-01-01'),
variables: { temperature: 25, ice_cream_sales: 100, happiness: 8 },
context: { season: 'summer', location: 'park' }
},
{
timestamp: new Date('2024-01-02'),
variables: { temperature: 30, ice_cream_sales: 150, happiness: 9 },
context: { season: 'summer', location: 'park' }
},
{
timestamp: new Date('2024-01-03'),
variables: { temperature: 20, ice_cream_sales: 80, happiness: 7 },
context: { season: 'summer', location: 'park' }
},
{
timestamp: new Date('2024-01-04'),
variables: { temperature: 35, ice_cream_sales: 200, happiness: 10 },
context: { season: 'summer', location: 'park' }
},
{
timestamp: new Date('2024-01-05'),
variables: { temperature: 15, ice_cream_sales: 50, happiness: 6 },
context: { season: 'summer', location: 'park' }
}
],
parameters: {
method: 'correlation',
significance: 0.5,
minSamples: 3,
maxLag: 1
}
};
const result = await causalReasoningEngine.learnCausalRelationships(learningRequest);
expect(result).toBeDefined();
expect(result.discoveredRelationships).toBeDefined();
expect(result.statistics.totalObservations).toBe(5);
expect(result.statistics.relationshipsFound).toBeGreaterThanOrEqual(0);
if (result.discoveredRelationships.length > 0) {
expect(result.discoveredRelationships[0]).toHaveProperty('cause');
expect(result.discoveredRelationships[0]).toHaveProperty('effect');
expect(result.discoveredRelationships[0]).toHaveProperty('strength');
expect(result.discoveredRelationships[0]).toHaveProperty('confidence');
}
});
it('should analyze causal patterns and provide insights', async () => {
if (shouldSkipTest() || !causalCollection || !causalReasoningEngine) return;
const agentId = 'test_agent_causal_005';
// Add some test relationships first
await causalCollection.storeCausalRelationship({
agentId,
timestamp: new Date(),
relationship: {
id: 'exercise_health',
type: 'direct',
category: 'physical',
strength: 0.85,
confidence: 0.9,
cause: {
id: 'exercise',
name: 'Exercise',
description: 'Physical activity',
type: 'action',
attributes: {},
context: { temporal: {}, spatial: {}, social: {}, environmental: {} }
},
effect: {
id: 'health',
name: 'Health',
description: 'Physical wellbeing',
type: 'state',
attributes: {},
magnitude: 0.8,
probability: 0.85,
delay: 0,
duration: 86400000
},
mechanism: {
description: 'Exercise improves cardiovascular health and fitness',
steps: [],
conditions: [],
moderators: []
}
},
evidence: {
empirical: { observations: [], experiments: [], correlations: [] },
theoretical: { theories: [], models: [], analogies: [] },
counterEvidence: []
},
network: { parentCauses: [], childEffects: [], confounders: [], alternatives: [] },
temporal: {
timing: { precedence: 'before', lag: 0, persistence: 86400000 },
patterns: { trend: 'increasing' },
history: []
},
inference: {
methods: [],
reasoning: [],
uncertainty: { epistemic: 0.1, aleatory: 0.05, model: 0.05, measurement: 0.02 }
},
learning: {
updates: [],
predictions: [],
performance: { accuracy: 0.85, precision: 0.85, recall: 0.85, f1Score: 0.85, calibration: 0.85 }
},
metadata: {
framework: 'test',
version: '1.0.0',
source: 'test',
reliability: 0.85,
lastValidated: new Date(),
quality: { completeness: 0.9, consistency: 0.9, coherence: 0.9, plausibility: 0.9 }
}
});
const patterns = await causalReasoningEngine.getCausalPatterns(agentId);
expect(patterns).toBeDefined();
expect(patterns.strongestCauses).toBeDefined();
expect(patterns.commonEffects).toBeDefined();
expect(patterns.causalCategories).toBeDefined();
expect(patterns.temporalPatterns).toBeDefined();
});
});
describe('Error Handling and Edge Cases', () => {
it('should handle uninitialized engine gracefully', async () => {
if (shouldSkipTest() || !db) return;
const uninitializedEngine = new CausalReasoningEngine(db);
const inferenceRequest: CausalInferenceRequest = {
agentId: 'test_agent',
scenario: { description: 'test' },
query: { type: 'what_if', cause: 'test_cause' },
parameters: { maxDepth: 1, minStrength: 0.5, minConfidence: 0.5, includeIndirect: false }
};
await expect(uninitializedEngine.performCausalInference(inferenceRequest))
.rejects.toThrow('CausalReasoningEngine not initialized');
});
it('should handle invalid causal queries gracefully', async () => {
if (shouldSkipTest() || !causalReasoningEngine) return;
const invalidRequest: CausalInferenceRequest = {
agentId: 'test_agent',
scenario: { description: 'test' },
query: { type: 'what_if' }, // Missing cause or effect
parameters: { maxDepth: 1, minStrength: 0.5, minConfidence: 0.5, includeIndirect: false }
};
await expect(causalReasoningEngine.performCausalInference(invalidRequest))
.rejects.toThrow('Either cause or effect must be specified in query');
});
});
console.log(`
🎯 CAUSAL REASONING ENGINE - COMPREHENSIVE TEST SUMMARY
======================================================
This comprehensive test demonstrates the CausalReasoningEngine's capabilities:
✅ MONGODB ATLAS FEATURES SHOWCASED:
• $graphLookup for recursive causal chain traversal
• Graph operations for cause-effect relationship mapping
• Complex aggregation pipelines for causal pattern analysis
• Rich document storage for causal relationship metadata
• Efficient indexing for causal reasoning queries
🧠 CAUSAL REASONING CAPABILITIES:
• Causal relationship storage and retrieval
• Recursive causal chain traversal using MongoDB $graphLookup
• What-if analysis and counterfactual reasoning
• Causal learning from observational data
• Pattern recognition in causal networks
• Uncertainty quantification in causal inference
• Alternative explanation generation
• Confounding factor identification
🔬 ADVANCED FEATURES:
• Multi-level causal analysis with depth tracking
• Temporal precedence checking
• Causal strength and confidence calculation
• Evidence-based causal validation
• Mechanism-based causal explanation
• Graph-based causal network analysis
📊 REAL-WORLD APPLICATIONS:
• Scientific hypothesis testing
• Business decision making
• Medical diagnosis and treatment
• Policy impact analysis
• Risk assessment and management
• Predictive modeling and forecasting
This engine represents a breakthrough in AI causal reasoning capabilities,
leveraging MongoDB's powerful graph operations for sophisticated causal analysis.
`);
});