"use strict"; /** * ADVANCED TUTORIAL: Custom Learning System * * Extend the self-learning system with custom optimization strategies, * domain-specific learning, and advanced evaluation metrics. Perfect for * building production-grade adaptive AI systems. * * What you'll learn: * - Creating custom evaluators * - Domain-specific optimization * - Advanced feedback loops * - Multi-objective optimization * - Transfer learning patterns * * Prerequisites: * - Complete intermediate tutorials first * - Set GEMINI_API_KEY environment variable * - npm install dspy.ts @ruvector/agentic-synth * * Run: npx tsx examples/advanced/custom-learning-system.ts */ Object.defineProperty(exports, "__esModule", { value: true }); exports.EcommerceEvaluator = exports.AdvancedLearningSystem = void 0; const dspy_ts_1 = require("dspy.ts"); // Domain-specific evaluator for e-commerce class EcommerceEvaluator { async evaluate(output, context) { const metrics = { accuracy: 0, creativity: 0, relevance: 0, engagement: 0, technicalQuality: 0, overall: 0 }; // Accuracy: Check for required information if (output.description && output.key_features) { metrics.accuracy += 0.5; // Check if key product attributes are mentioned const desc = output.description.toLowerCase(); const productName = context.product_name.toLowerCase(); const category = context.category.toLowerCase(); if (desc.includes(productName.split(' ')[0])) { metrics.accuracy += 0.25; } if (desc.includes(category)) { metrics.accuracy += 0.25; } } // Creativity: Check for unique, non-generic phrases if (output.description) { const genericPhrases = ['high quality', 'great product', 'best choice']; const hasGenericPhrase = genericPhrases.some(phrase => output.description.toLowerCase().includes(phrase)); metrics.creativity = hasGenericPhrase ? 0.3 : 0.8; // Bonus for specific details const hasNumbers = /\d+/.test(output.description); const hasSpecifics = /(\d+\s*(hours|days|years|gb|mb|kg|lbs))/i.test(output.description); if (hasSpecifics) metrics.creativity += 0.2; } // Relevance: Check alignment with category const categoryKeywords = { electronics: ['technology', 'device', 'digital', 'battery', 'power'], fashion: ['style', 'design', 'material', 'comfort', 'wear'], food: ['taste', 'flavor', 'nutrition', 'organic', 'fresh'], fitness: ['workout', 'exercise', 'health', 'training', 'performance'] }; const category = context.category.toLowerCase(); const relevantKeywords = categoryKeywords[category] || []; if (output.description) { const desc = output.description.toLowerCase(); const matchedKeywords = relevantKeywords.filter(kw => desc.includes(kw)); metrics.relevance = Math.min(matchedKeywords.length / 3, 1.0); } // Engagement: Check for emotional appeal and calls to action if (output.description) { const desc = output.description.toLowerCase(); const emotionalWords = ['amazing', 'incredible', 'perfect', 'premium', 'exceptional', 'revolutionary']; const actionWords = ['discover', 'experience', 'enjoy', 'upgrade', 'transform']; const hasEmotion = emotionalWords.some(word => desc.includes(word)); const hasAction = actionWords.some(word => desc.includes(word)); metrics.engagement = (hasEmotion ? 0.5 : 0) + (hasAction ? 0.5 : 0); } // Technical Quality: Check structure and formatting if (output.key_features && Array.isArray(output.key_features)) { const features = output.key_features; let techScore = 0; // Optimal number of features if (features.length >= 4 && features.length <= 6) { techScore += 0.4; } // Feature formatting const wellFormatted = features.filter(f => f.length >= 15 && f.length <= 60 && !f.endsWith('.')); techScore += (wellFormatted.length / features.length) * 0.6; metrics.technicalQuality = techScore; } // Calculate overall score with weights metrics.overall = (metrics.accuracy * 0.25 + metrics.creativity * 0.20 + metrics.relevance * 0.25 + metrics.engagement * 0.15 + metrics.technicalQuality * 0.15); return metrics; } } exports.EcommerceEvaluator = EcommerceEvaluator; // Advanced self-learning generator class AdvancedLearningSystem { constructor(config, evaluator) { this.knowledgeBase = []; this.promptStrategies = new Map(); this.config = config; this.evaluator = evaluator; this.lm = new dspy_ts_1.LM({ provider: 'google-genai', model: 'gemini-2.0-flash-exp', apiKey: process.env.GEMINI_API_KEY || '', temperature: this.getTemperatureForStrategy() }); } getTemperatureForStrategy() { switch (this.config.learningStrategy) { case 'aggressive': return 0.9; case 'conservative': return 0.5; case 'adaptive': return 0.7; } } // Learn from a single example async learnFromExample(example) { console.log(`\n๐ŸŽฏ Learning from example (${example.metadata.difficulty})...`); const output = await this.generate(example.input); const metrics = await this.evaluator.evaluate(output, example.input); console.log(` Overall Quality: ${(metrics.overall * 100).toFixed(1)}%`); console.log(` Accuracy: ${(metrics.accuracy * 100).toFixed(0)}% | Creativity: ${(metrics.creativity * 100).toFixed(0)}%`); console.log(` Relevance: ${(metrics.relevance * 100).toFixed(0)}% | Engagement: ${(metrics.engagement * 100).toFixed(0)}%`); // Store high-quality examples if (metrics.overall >= 0.7) { this.knowledgeBase.push({ ...example, quality: metrics.overall }); console.log(` โœ“ Added to knowledge base`); } } // Train on a dataset async train(examples) { console.log('๐Ÿ‹๏ธ Starting Advanced Training Session\n'); console.log('='.repeat(70)); console.log(`\nDomain: ${this.config.domain}`); console.log(`Strategy: ${this.config.learningStrategy}`); console.log(`Examples: ${examples.length}`); console.log(`\nObjectives:`); this.config.objectives.forEach(obj => console.log(` โ€ข ${obj}`)); console.log('\n' + '='.repeat(70)); // Group by difficulty const byDifficulty = { easy: examples.filter(e => e.metadata.difficulty === 'easy'), medium: examples.filter(e => e.metadata.difficulty === 'medium'), hard: examples.filter(e => e.metadata.difficulty === 'hard') }; // Progressive learning: start with easy, move to hard console.log('\n๐Ÿ“š Phase 1: Learning Basics (Easy Examples)'); console.log('โ”€'.repeat(70)); for (const example of byDifficulty.easy) { await this.learnFromExample(example); } console.log('\n๐Ÿ“š Phase 2: Intermediate Concepts (Medium Examples)'); console.log('โ”€'.repeat(70)); for (const example of byDifficulty.medium) { await this.learnFromExample(example); } console.log('\n๐Ÿ“š Phase 3: Advanced Patterns (Hard Examples)'); console.log('โ”€'.repeat(70)); for (const example of byDifficulty.hard) { await this.learnFromExample(example); } this.displayTrainingResults(); } // Generate with learned knowledge async generate(input) { // Use knowledge base for few-shot learning const similarExamples = this.findSimilarExamples(input, 3); let enhancedDescription = 'Generate compelling product descriptions.'; if (similarExamples.length > 0) { enhancedDescription += '\n\nLearn from these high-quality examples:\n'; similarExamples.forEach((ex, i) => { enhancedDescription += `\nExample ${i + 1}:\n`; enhancedDescription += `Input: ${JSON.stringify(ex.input)}\n`; enhancedDescription += `Output: ${JSON.stringify(ex.expectedOutput)}`; }); } const signature = { input: 'product_name: string, category: string, price: number', output: 'description: string, key_features: string[]', description: enhancedDescription }; const generator = new dspy_ts_1.ChainOfThought(signature, { lm: this.lm }); return await generator.forward(input); } // Find similar examples from knowledge base findSimilarExamples(input, count) { // Simple similarity based on category match const similar = this.knowledgeBase .filter(ex => ex.input.category === input.category) .sort((a, b) => b.quality - a.quality) .slice(0, count); return similar; } // Display training results displayTrainingResults() { console.log('\n\n' + '='.repeat(70)); console.log('\n๐ŸŽ“ TRAINING RESULTS\n'); console.log(`Knowledge Base: ${this.knowledgeBase.length} high-quality examples`); if (this.knowledgeBase.length > 0) { const avgQuality = this.knowledgeBase.reduce((sum, ex) => sum + ex.quality, 0) / this.knowledgeBase.length; console.log(`Average Quality: ${(avgQuality * 100).toFixed(1)}%`); // Group by category const byCategory = {}; this.knowledgeBase.forEach(ex => { const cat = ex.input.category; byCategory[cat] = (byCategory[cat] || 0) + 1; }); console.log(`\nLearned Categories:`); Object.entries(byCategory).forEach(([cat, count]) => { console.log(` โ€ข ${cat}: ${count} examples`); }); } console.log('\nโœ… Training complete! System is ready for production.\n'); console.log('='.repeat(70) + '\n'); } // Test the trained system async test(testCases) { console.log('\n๐Ÿงช Testing Trained System\n'); console.log('='.repeat(70) + '\n'); let totalMetrics = { accuracy: 0, creativity: 0, relevance: 0, engagement: 0, technicalQuality: 0, overall: 0 }; for (let i = 0; i < testCases.length; i++) { const testCase = testCases[i]; console.log(`\nTest ${i + 1}/${testCases.length}: ${testCase.product_name}`); console.log('โ”€'.repeat(70)); const output = await this.generate(testCase); const metrics = await this.evaluator.evaluate(output, testCase); console.log(`\n๐Ÿ“ Generated:`); console.log(` ${output.description}`); console.log(`\n Features:`); if (output.key_features) { output.key_features.forEach((f) => console.log(` โ€ข ${f}`)); } console.log(`\n๐Ÿ“Š Metrics:`); console.log(` Overall: ${(metrics.overall * 100).toFixed(1)}%`); console.log(` Accuracy: ${(metrics.accuracy * 100).toFixed(0)}% | Creativity: ${(metrics.creativity * 100).toFixed(0)}%`); console.log(` Relevance: ${(metrics.relevance * 100).toFixed(0)}% | Engagement: ${(metrics.engagement * 100).toFixed(0)}%`); console.log(` Technical: ${(metrics.technicalQuality * 100).toFixed(0)}%`); // Aggregate metrics Object.keys(totalMetrics).forEach(key => { totalMetrics[key] += metrics[key]; }); } // Average metrics Object.keys(totalMetrics).forEach(key => { totalMetrics[key] /= testCases.length; }); console.log('\n\n' + '='.repeat(70)); console.log('\n๐Ÿ“ˆ TEST SUMMARY\n'); console.log(`Overall Performance: ${(totalMetrics.overall * 100).toFixed(1)}%`); console.log(`\nDetailed Metrics:`); console.log(` Accuracy: ${(totalMetrics.accuracy * 100).toFixed(1)}%`); console.log(` Creativity: ${(totalMetrics.creativity * 100).toFixed(1)}%`); console.log(` Relevance: ${(totalMetrics.relevance * 100).toFixed(1)}%`); console.log(` Engagement: ${(totalMetrics.engagement * 100).toFixed(1)}%`); console.log(` Technical Quality: ${(totalMetrics.technicalQuality * 100).toFixed(1)}%`); console.log('\n' + '='.repeat(70) + '\n'); } } exports.AdvancedLearningSystem = AdvancedLearningSystem; // Main execution async function runAdvancedLearning() { const config = { domain: 'ecommerce', objectives: [ 'Generate accurate product descriptions', 'Maintain high creativity and engagement', 'Ensure category-specific relevance' ], weights: { accuracy: 0.25, creativity: 0.20, relevance: 0.25, engagement: 0.15, technical: 0.15 }, learningStrategy: 'adaptive', convergenceThreshold: 0.85, diversityBonus: true, transferLearning: true }; const evaluator = new EcommerceEvaluator(); const system = new AdvancedLearningSystem(config, evaluator); // Training examples const trainingExamples = [ { input: { product_name: 'Smart Watch', category: 'electronics', price: 299 }, expectedOutput: { description: 'Advanced fitness tracking meets elegant design in this premium smartwatch', key_features: ['Heart rate monitoring', '7-day battery', 'Water resistant', 'GPS tracking'] }, quality: 0.9, metadata: { domain: 'ecommerce', difficulty: 'easy', tags: ['electronics', 'wearable'] } }, { input: { product_name: 'Yoga Mat', category: 'fitness', price: 49 }, expectedOutput: { description: 'Professional-grade yoga mat with superior grip and cushioning for all practice levels', key_features: ['6mm thickness', 'Non-slip surface', 'Eco-friendly material', 'Easy to clean'] }, quality: 0.85, metadata: { domain: 'ecommerce', difficulty: 'easy', tags: ['fitness', 'yoga'] } }, { input: { product_name: 'Mechanical Keyboard', category: 'electronics', price: 159 }, expectedOutput: { description: 'Tactile perfection for enthusiasts with customizable RGB and premium switches', key_features: ['Cherry MX switches', 'RGB backlighting', 'Programmable keys', 'Aluminum frame'] }, quality: 0.92, metadata: { domain: 'ecommerce', difficulty: 'medium', tags: ['electronics', 'gaming'] } } ]; // Train the system await system.train(trainingExamples); // Test the system const testCases = [ { product_name: 'Wireless Earbuds', category: 'electronics', price: 129 }, { product_name: 'Resistance Bands Set', category: 'fitness', price: 29 }, { product_name: 'Laptop Stand', category: 'electronics', price: 59 } ]; await system.test(testCases); } // Run the example if (import.meta.url === `file://${process.argv[1]}`) { runAdvancedLearning().catch(error => { console.error('โŒ Advanced learning failed:', error); process.exit(1); }); } //# sourceMappingURL=custom-learning-system.js.map