feat: add Universal Display Augmentation for AI-powered enhanced output

- Implements intelligent display fields with AI-generated titles and descriptions
- Leverages existing IntelligentTypeMatcher for semantic type detection
- Adds lazy computation with LRU caching for zero performance impact
- Enhances CLI with clean, minimal formatting (no visual clutter)
- Provides method-based API (getDisplay()) to avoid namespace conflicts
- Maintains 100% backward compatibility with existing code
- Enables by default with complete isolation architecture
- Includes comprehensive tests and documentation

The augmentation transforms search results and data display with smart,
contextual information while maintaining Soulcraft's clean aesthetic.
This commit is contained in:
David Snelling 2025-08-28 12:37:07 -07:00
parent 5c44616336
commit 4b58b8af01
11 changed files with 3511 additions and 62 deletions

View file

@ -0,0 +1,448 @@
/**
* Universal Display Augmentation Tests
*
* Comprehensive test suite for the display augmentation system
* including AI-powered field computation, caching, and CLI integration
*/
import { describe, it, expect, beforeEach, afterEach } from 'vitest'
import { BrainyData } from '../src/brainyData.js'
import { UniversalDisplayAugmentation } from '../src/augmentations/universalDisplayAugmentation.js'
import { DisplayCache } from '../src/augmentations/display/cache.js'
import { IntelligentComputationEngine } from '../src/augmentations/display/intelligentComputation.js'
describe('Universal Display Augmentation', () => {
let brainy: BrainyData
let displayAugmentation: UniversalDisplayAugmentation
beforeEach(async () => {
// Use in-memory storage for tests
brainy = new BrainyData({
storage: { forceMemoryStorage: true },
verbose: false
})
await brainy.init()
// Get display augmentation (should be enabled by default)
const augmentations = (brainy as any).augmentations
displayAugmentation = augmentations?.get('display')
})
afterEach(async () => {
if (brainy) {
await brainy.clearAll({ force: true })
}
})
describe('Augmentation Setup', () => {
it('should be enabled by default', () => {
expect(displayAugmentation).toBeDefined()
expect(displayAugmentation.name).toBe('display')
expect(displayAugmentation.version).toBe('1.0.0')
})
it('should have correct metadata access configuration', () => {
expect(displayAugmentation.metadata).toEqual({
reads: '*',
writes: ['_display']
})
})
it('should declare computed fields', () => {
expect(displayAugmentation.computedFields).toBeDefined()
expect(displayAugmentation.computedFields.display).toBeDefined()
expect(displayAugmentation.computedFields.display.title).toEqual({
type: 'string',
description: 'Primary display name (AI-computed)'
})
})
it('should have correct operation targeting', () => {
expect(displayAugmentation.operations).toContain('get')
expect(displayAugmentation.operations).toContain('search')
expect(displayAugmentation.operations).toContain('findSimilar')
})
})
describe('Display Field Computation', () => {
it('should enhance noun results with display fields', async () => {
// Add test data
const id = await brainy.addNoun('John Doe', {
type: 'Person',
role: 'CEO',
company: 'Acme Corp'
})
// Get the enhanced result
const result = await brainy.getNoun(id)
// Should have display capabilities
expect(result.getDisplay).toBeDefined()
expect(typeof result.getDisplay).toBe('function')
// Test display fields
const displayFields = await result.getDisplay()
expect(displayFields).toBeDefined()
expect(displayFields.title).toBeDefined()
expect(displayFields.type).toBeDefined()
expect(displayFields.icon).toBeDefined()
expect(displayFields.description).toBeDefined()
expect(displayFields.confidence).toBeGreaterThan(0)
})
it('should provide type-appropriate icons', async () => {
const testCases = [
{ data: 'Apple Inc', metadata: { type: 'Organization' }, expectedIcon: '🏢' },
{ data: 'Jane Smith', metadata: { type: 'Person' }, expectedIcon: '👤' },
{ data: 'San Francisco', metadata: { type: 'Location' }, expectedIcon: '📍' },
{ data: 'Machine Learning', metadata: { type: 'Concept' }, expectedIcon: '💭' }
]
for (const testCase of testCases) {
const id = await brainy.addNoun(testCase.data, testCase.metadata)
const result = await brainy.getNoun(id)
const displayFields = await result.getDisplay()
expect(displayFields.icon).toBe(testCase.expectedIcon)
expect(displayFields.type).toBeDefined()
}
})
it('should handle missing or minimal metadata gracefully', async () => {
// Add data with minimal metadata
const id = await brainy.addNoun('Some random text')
const result = await brainy.getNoun(id)
const displayFields = await result.getDisplay()
expect(displayFields.title).toBeDefined()
expect(displayFields.type).toBeDefined()
expect(displayFields.icon).toBeDefined()
expect(displayFields.confidence).toBeGreaterThan(0)
})
it('should compute enhanced descriptions', async () => {
const id = await brainy.addNoun('Tesla Model 3', {
type: 'Product',
category: 'Electric Vehicle',
manufacturer: 'Tesla'
})
const result = await brainy.getNoun(id)
const displayFields = await result.getDisplay()
expect(displayFields.description).toBeDefined()
expect(displayFields.description.length).toBeGreaterThan(displayFields.title.length)
})
})
describe('Search Result Enhancement', () => {
beforeEach(async () => {
// Add test data for search
await brainy.addNoun('John Doe', { type: 'Person', role: 'CEO' })
await brainy.addNoun('Apple Inc', { type: 'Organization', industry: 'Technology' })
await brainy.addNoun('MacBook Pro', { type: 'Product', brand: 'Apple' })
})
it('should enhance search results', async () => {
const results = await brainy.search('CEO', { limit: 5 })
expect(results.length).toBeGreaterThan(0)
// Check that results are enhanced
const firstResult = results[0]
expect(firstResult.getDisplay).toBeDefined()
const displayFields = await firstResult.getDisplay()
expect(displayFields.title).toBeDefined()
expect(displayFields.icon).toBeDefined()
})
it('should maintain search scores while adding display fields', async () => {
const results = await brainy.search('Apple', { limit: 5 })
expect(results.length).toBeGreaterThan(0)
const firstResult = results[0]
expect(firstResult.score).toBeDefined()
expect(firstResult.getDisplay).toBeDefined()
})
})
describe('Verb Display Enhancement', () => {
it('should enhance verb relationships with display fields', async () => {
// Add entities and relationship
const johnId = await brainy.addNoun('John Doe', { type: 'Person' })
const appleId = await brainy.addNoun('Apple Inc', { type: 'Organization' })
const verbId = await brainy.addVerb(johnId, appleId, 'WorksFor')
// Get the enhanced verb
const verb = await brainy.getVerb(verbId)
expect(verb.getDisplay).toBeDefined()
const displayFields = await verb.getDisplay()
expect(displayFields.relationship).toBeDefined()
expect(displayFields.icon).toBeDefined()
expect(displayFields.type).toBeDefined()
})
})
describe('Caching System', () => {
it('should cache computed display fields', async () => {
const id = await brainy.addNoun('Test Entity', { type: 'Concept' })
const result = await brainy.getNoun(id)
// First computation
const displayFields1 = await result.getDisplay()
// Second computation should be cached
const displayFields2 = await result.getDisplay()
// Should be identical (cached)
expect(displayFields1).toEqual(displayFields2)
// Check cache statistics
const stats = displayAugmentation.getStats()
expect(stats.totalComputations).toBeGreaterThan(0)
})
it('should provide cache statistics', () => {
const stats = displayAugmentation.getStats()
expect(stats).toBeDefined()
expect(stats.totalComputations).toBeDefined()
expect(stats.cacheHitRatio).toBeDefined()
expect(stats.averageComputationTime).toBeDefined()
})
})
describe('Helper Methods', () => {
it('should provide getAvailableFields method', async () => {
const id = await brainy.addNoun('Test Entity')
const result = await brainy.getNoun(id)
expect(result.getAvailableFields).toBeDefined()
const fields = result.getAvailableFields('display')
expect(Array.isArray(fields)).toBe(true)
expect(fields).toContain('title')
expect(fields).toContain('description')
expect(fields).toContain('type')
expect(fields).toContain('icon')
})
it('should provide getAvailableAugmentations method', async () => {
const id = await brainy.addNoun('Test Entity')
const result = await brainy.getNoun(id)
expect(result.getAvailableAugmentations).toBeDefined()
const augs = result.getAvailableAugmentations()
expect(Array.isArray(augs)).toBe(true)
expect(augs).toContain('display')
})
it('should provide explore method for debugging', async () => {
const id = await brainy.addNoun('Test Entity', { type: 'Concept', description: 'Test' })
const result = await brainy.getNoun(id)
expect(result.explore).toBeDefined()
// Should not throw when called
await expect(result.explore()).resolves.toBeUndefined()
})
})
describe('Configuration', () => {
it('should support runtime configuration', () => {
const newConfig = {
enabled: false,
cacheSize: 500
}
displayAugmentation.configure(newConfig)
// Configuration should be applied
expect((displayAugmentation as any).config.enabled).toBe(false)
expect((displayAugmentation as any).config.cacheSize).toBe(500)
})
it('should clear cache when disabled', () => {
displayAugmentation.configure({ enabled: false })
// Cache should be cleared
const stats = displayAugmentation.getStats()
expect(stats.totalComputations).toBe(0)
})
})
describe('Error Handling', () => {
it('should handle computation errors gracefully', async () => {
// Add data that might cause computation issues
const id = await brainy.addNoun('') // Empty string
const result = await brainy.getNoun(id)
// Should still provide display fields, even if basic
const displayFields = await result.getDisplay()
expect(displayFields).toBeDefined()
expect(displayFields.title).toBeDefined()
expect(displayFields.icon).toBeDefined()
})
it('should work without AI components', async () => {
// Test fallback to heuristic-based computation
const id = await brainy.addNoun('Test Without AI', { type: 'Thing' })
const result = await brainy.getNoun(id)
// Should still work with heuristic fallback
const displayFields = await result.getDisplay()
expect(displayFields).toBeDefined()
expect(displayFields.title).toBeDefined()
expect(displayFields.type).toBeDefined()
})
})
describe('Performance', () => {
it('should have reasonable computation times', async () => {
const startTime = Date.now()
const id = await brainy.addNoun('Performance Test Entity', {
type: 'Concept',
description: 'Testing performance characteristics'
})
const result = await brainy.getNoun(id)
await result.getDisplay()
const endTime = Date.now()
const duration = endTime - startTime
// Should complete within reasonable time (adjust based on system capabilities)
expect(duration).toBeLessThan(5000) // 5 seconds max
})
it('should handle batch operations efficiently', async () => {
const startTime = Date.now()
const ids: string[] = []
// Add multiple entities
for (let i = 0; i < 10; i++) {
const id = await brainy.addNoun(`Test Entity ${i}`, { type: 'Concept' })
ids.push(id)
}
// Get display fields for all
const displayPromises = ids.map(async id => {
const result = await brainy.getNoun(id)
return result.getDisplay()
})
await Promise.all(displayPromises)
const endTime = Date.now()
const duration = endTime - startTime
// Batch should be reasonably fast
expect(duration).toBeLessThan(10000) // 10 seconds max for 10 items
})
})
describe('Shutdown and Cleanup', () => {
it('should shutdown gracefully', async () => {
// Should not throw
await expect(displayAugmentation.shutdown()).resolves.toBeUndefined()
})
it('should clear cache on shutdown', async () => {
displayAugmentation.clearCache()
const stats = displayAugmentation.getStats()
expect(stats.totalComputations).toBe(0)
expect(stats.cacheHitRatio).toBe(0)
})
})
})
describe('Display Cache', () => {
let cache: DisplayCache
beforeEach(() => {
cache = new DisplayCache(100)
})
it('should store and retrieve display fields', () => {
const testFields = {
title: 'Test Title',
description: 'Test Description',
type: 'Test Type',
icon: '📝',
tags: ['test'],
confidence: 0.9,
computedAt: Date.now(),
version: '1.0.0'
}
const key = cache.generateKey('test-id', { name: 'test' }, 'noun')
cache.set(key, testFields)
const retrieved = cache.get(key)
expect(retrieved).toEqual(testFields)
})
it('should implement LRU eviction', () => {
const smallCache = new DisplayCache(2)
const fields = {
title: 'Test',
description: 'Test',
type: 'Test',
icon: '📝',
tags: [],
confidence: 0.9,
computedAt: Date.now(),
version: '1.0.0'
}
// Fill cache to capacity
smallCache.set('key1', fields)
smallCache.set('key2', fields)
// Add one more (should evict oldest)
smallCache.set('key3', fields)
// key1 should be evicted
expect(smallCache.get('key1')).toBeNull()
expect(smallCache.get('key2')).toBeDefined()
expect(smallCache.get('key3')).toBeDefined()
})
it('should generate consistent cache keys', () => {
const data = { name: 'test', type: 'Person' }
const key1 = cache.generateKey('id-123', data, 'noun')
const key2 = cache.generateKey('id-123', data, 'noun')
expect(key1).toBe(key2)
// Different entity type should produce different key
const key3 = cache.generateKey('id-123', data, 'verb')
expect(key1).not.toBe(key3)
})
it('should provide cache statistics', () => {
const fields = {
title: 'Test',
description: 'Test',
type: 'Test',
icon: '📝',
tags: [],
confidence: 0.9,
computedAt: Date.now(),
version: '1.0.0'
}
cache.set('test-key', fields, 100) // 100ms computation time
cache.get('test-key') // Hit
cache.get('nonexistent') // Miss
const stats = cache.getStats()
expect(stats.totalComputations).toBe(1)
expect(stats.cacheHitRatio).toBe(0.5) // 1 hit, 1 miss
expect(stats.averageComputationTime).toBe(100)
})
})