tasq/node_modules/agentdb/simulation/docs/architecture/EXTENSION-API.md

21 KiB

AgentDB Extension API v2.0

Overview

This document defines the Extension API for creating custom simulation scenarios, components, and integrations with AgentDB v2.0.


Table of Contents

  1. Creating Custom Scenarios
  2. Component Interfaces
  3. Plugin System
  4. Event System
  5. Code Examples

Creating Custom Scenarios

Scenario Interface

All simulation scenarios must implement the SimulationScenario interface:

interface SimulationScenario {
  metadata: SimulationMetadata;
  execute(config: AgentDBConfig): Promise<SimulationResult>;
  validate?(config: AgentDBConfig): ValidationResult;
  cleanup?(): Promise<void>;
}

interface SimulationMetadata {
  id: string;
  name: string;
  version: string;
  category: 'core' | 'experimental' | 'plugin';
  description: string;
  author?: string;
  agentdbVersion: string; // Semver range (e.g., "^2.0.0")
  tags?: string[];
  estimatedDuration?: number; // milliseconds
  requiredMemoryMB?: number;
}

interface AgentDBConfig {
  profile: 'production' | 'memory' | 'latency' | 'recall' | 'custom';
  hnsw: { M: number; efConstruction: number; efSearch: number };
  attention: { heads: number; dimension: number };
  traversal: { beamWidth: number; strategy: 'greedy' | 'beam' | 'dynamic' };
  clustering: { algorithm: 'louvain' | 'leiden' | 'spectral'; resolution: number };
  neural: { mode: 'none' | 'gnn-only' | 'full'; reinforcementLearning: boolean };
  hypergraph: { enabled: boolean; maxEdgeSize: number };
  storage: { reportPath: string; autoBackup: boolean };
  monitoring: { enabled: boolean; alertThresholds: { memoryMB: number; latencyMs: number } };
}

interface SimulationResult {
  scenario: string;
  timestamp: Date;
  config: AgentDBConfig;
  metrics: {
    recall: number;
    latency: number;
    throughput: number;
    memoryUsage: number;
    [key: string]: any;
  };
  insights: string[];
  recommendations: string[];
  iterations?: number;
  duration?: number;
}

interface ValidationResult {
  valid: boolean;
  errors?: string[];
  warnings?: string[];
}

Minimal Example

// ~/.agentdb/plugins/my-scenario/index.ts
import { SimulationScenario, SimulationResult, AgentDBConfig } from 'agentdb';

export const myScenario: SimulationScenario = {
  metadata: {
    id: 'my-custom-scenario',
    name: 'My Custom Scenario',
    version: '1.0.0',
    category: 'plugin',
    description: 'Custom simulation for specific use case',
    author: 'Your Name',
    agentdbVersion: '^2.0.0',
    tags: ['custom', 'experimental'],
    estimatedDuration: 30000, // 30 seconds
    requiredMemoryMB: 512
  },

  async execute(config: AgentDBConfig): Promise<SimulationResult> {
    // Your simulation logic here
    console.log('Running custom scenario...');

    // Example: Simulate HNSW search
    const recall = 0.95;
    const latency = 120;
    const throughput = 1000;
    const memoryUsage = 512;

    return {
      scenario: this.metadata.id,
      timestamp: new Date(),
      config,
      metrics: {
        recall,
        latency,
        throughput,
        memoryUsage
      },
      insights: [
        'Custom insight 1: Performance is optimal',
        'Custom insight 2: Memory usage is within bounds'
      ],
      recommendations: [
        'Try increasing M parameter for better recall',
        'Consider enabling neural augmentation'
      ],
      iterations: 1,
      duration: 25000
    };
  },

  validate(config: AgentDBConfig): ValidationResult {
    const errors: string[] = [];
    const warnings: string[] = [];

    // Custom validation logic
    if (config.hnsw.M < 16) {
      errors.push('M must be at least 16 for this scenario');
    }

    if (config.neural.mode === 'none') {
      warnings.push('Neural mode recommended for best results');
    }

    return {
      valid: errors.length === 0,
      errors: errors.length > 0 ? errors : undefined,
      warnings: warnings.length > 0 ? warnings : undefined
    };
  },

  async cleanup(): Promise<void> {
    // Optional cleanup logic
    console.log('Cleaning up custom scenario...');
  }
};

export default myScenario;

Advanced Example with Progress Tracking

import { SimulationScenario, SimulationResult, AgentDBConfig } from 'agentdb';
import { EventEmitter } from 'events';

export class AdvancedScenario extends EventEmitter implements SimulationScenario {
  metadata = {
    id: 'advanced-scenario',
    name: 'Advanced Scenario',
    version: '1.0.0',
    category: 'plugin' as const,
    description: 'Advanced simulation with progress tracking',
    agentdbVersion: '^2.0.0',
    estimatedDuration: 60000,
    requiredMemoryMB: 1024
  };

  async execute(config: AgentDBConfig): Promise<SimulationResult> {
    const totalIterations = 100;
    const metrics = {
      recall: 0,
      latency: 0,
      throughput: 0,
      memoryUsage: 0
    };

    for (let i = 0; i < totalIterations; i++) {
      // Simulate work
      await this.simulateIteration(i, config);

      // Emit progress
      this.emit('progress', {
        iteration: i + 1,
        total: totalIterations,
        percent: ((i + 1) / totalIterations) * 100
      });

      // Update metrics
      metrics.recall += Math.random() * 0.01;
      metrics.latency += Math.random() * 5;
    }

    metrics.recall /= totalIterations;
    metrics.latency /= totalIterations;
    metrics.throughput = 1000 / (metrics.latency / 1000);
    metrics.memoryUsage = process.memoryUsage().heapUsed / 1024 / 1024;

    return {
      scenario: this.metadata.id,
      timestamp: new Date(),
      config,
      metrics,
      insights: [
        `Achieved ${(metrics.recall * 100).toFixed(1)}% recall`,
        `Average latency: ${metrics.latency.toFixed(2)}ms`
      ],
      recommendations: this.generateRecommendations(metrics, config),
      iterations: totalIterations
    };
  }

  private async simulateIteration(iteration: number, config: AgentDBConfig): Promise<void> {
    // Simulate work with delay
    await new Promise(resolve => setTimeout(resolve, 100));
  }

  private generateRecommendations(metrics: any, config: AgentDBConfig): string[] {
    const recommendations: string[] = [];

    if (metrics.recall < 0.95) {
      recommendations.push('Increase beam width to improve recall');
    }

    if (metrics.latency > 200) {
      recommendations.push('Reduce efSearch to lower latency');
    }

    if (metrics.memoryUsage > config.monitoring.alertThresholds.memoryMB) {
      recommendations.push('Enable memory-constrained profile');
    }

    return recommendations;
  }
}

export default new AdvancedScenario();

Component Interfaces

SearchStrategy Interface

interface SearchStrategy {
  name: string;

  // Build index from vectors
  build(vectors: Vector[]): Promise<void>;

  // Search for k nearest neighbors
  search(query: Vector, k: number): Promise<SearchResult[]>;

  // Get index statistics
  getStats(): SearchStats;

  // Optional: Incremental updates
  insert?(vector: Vector): Promise<void>;
  delete?(id: string): Promise<void>;
}

interface Vector {
  id: string;
  data: number[];
  metadata?: Record<string, any>;
}

interface SearchResult {
  id: string;
  distance: number;
  vector: Vector;
}

interface SearchStats {
  totalVectors: number;
  dimensions: number;
  indexSize: number; // bytes
  buildTime: number; // ms
  avgSearchTime: number; // ms
}

Example Implementation:

class CustomSearchStrategy implements SearchStrategy {
  name = 'custom-hnsw';
  private index: Map<string, Vector> = new Map();

  async build(vectors: Vector[]): Promise<void> {
    const startTime = Date.now();

    for (const vector of vectors) {
      this.index.set(vector.id, vector);
    }

    console.log(`Built index in ${Date.now() - startTime}ms`);
  }

  async search(query: Vector, k: number): Promise<SearchResult[]> {
    const results: SearchResult[] = [];

    for (const [id, vector] of this.index.entries()) {
      const distance = this.calculateDistance(query.data, vector.data);
      results.push({ id, distance, vector });
    }

    results.sort((a, b) => a.distance - b.distance);
    return results.slice(0, k);
  }

  getStats(): SearchStats {
    return {
      totalVectors: this.index.size,
      dimensions: this.index.values().next().value?.data.length || 0,
      indexSize: 0, // Calculate actual size
      buildTime: 0,
      avgSearchTime: 0
    };
  }

  private calculateDistance(a: number[], b: number[]): number {
    // Euclidean distance
    return Math.sqrt(a.reduce((sum, val, i) => sum + Math.pow(val - b[i], 2), 0));
  }
}

ClusteringAlgorithm Interface

interface ClusteringAlgorithm {
  name: string;

  // Cluster graph into communities
  cluster(graph: Graph): Promise<Community[]>;

  // Get modularity score
  getModularity(): number;

  // Refine clustering
  refine(): Promise<void>;
}

interface Graph {
  nodes: Node[];
  edges: Edge[];
}

interface Node {
  id: string;
  data?: any;
}

interface Edge {
  source: string;
  target: string;
  weight?: number;
}

interface Community {
  id: string;
  nodes: string[];
  modularity: number;
}

Example Implementation:

class CustomClusteringAlgorithm implements ClusteringAlgorithm {
  name = 'custom-louvain';
  private communities: Community[] = [];
  private modularity: number = 0;

  async cluster(graph: Graph): Promise<Community[]> {
    // Implement Louvain algorithm
    // (simplified example)

    const communityMap = new Map<string, string[]>();

    for (const node of graph.nodes) {
      const communityId = `community-${Math.floor(Math.random() * 5)}`;

      if (!communityMap.has(communityId)) {
        communityMap.set(communityId, []);
      }

      communityMap.get(communityId)!.push(node.id);
    }

    this.communities = Array.from(communityMap.entries()).map(([id, nodes]) => ({
      id,
      nodes,
      modularity: this.calculateModularity(graph, nodes)
    }));

    this.modularity = this.communities.reduce((sum, c) => sum + c.modularity, 0);

    return this.communities;
  }

  getModularity(): number {
    return this.modularity;
  }

  async refine(): Promise<void> {
    // Implement refinement logic
  }

  private calculateModularity(graph: Graph, nodes: string[]): number {
    // Simplified modularity calculation
    return Math.random() * 0.5;
  }
}

NeuralAugmentation Interface

interface NeuralAugmentation {
  name: string;

  // Augment features with neural network
  augment(features: Tensor): Promise<Tensor>;

  // Train neural network
  train(samples: TrainingSample[]): Promise<void>;

  // Evaluate performance
  evaluate(): Promise<EvaluationMetrics>;
}

interface Tensor {
  shape: number[];
  data: number[];
}

interface TrainingSample {
  input: Tensor;
  target: Tensor;
}

interface EvaluationMetrics {
  accuracy: number;
  loss: number;
  f1Score: number;
}

Plugin System

Plugin Structure

~/.agentdb/plugins/my-plugin/
├── index.ts               # Main entry point
├── metadata.json          # Plugin metadata
├── package.json           # npm package (optional)
├── README.md              # Documentation
└── tests/                 # Tests (optional)
    └── index.test.ts

metadata.json

{
  "id": "my-custom-plugin",
  "name": "My Custom Plugin",
  "version": "1.0.0",
  "category": "plugin",
  "description": "Custom plugin for AgentDB",
  "author": "Your Name <your.email@example.com>",
  "agentdbVersion": "^2.0.0",
  "tags": ["custom", "experimental"],
  "estimatedDuration": 30000,
  "requiredMemoryMB": 512,
  "license": "MIT"
}

Installing Plugins

# Install from directory
agentdb plugin install ~/.agentdb/plugins/my-plugin

# Install from npm
agentdb plugin install my-agentdb-plugin

# Install from git
agentdb plugin install https://github.com/user/my-plugin.git

Listing Plugins

agentdb plugin list

Output:

📦 Installed Plugins:

✓ my-custom-plugin (v1.0.0)
  Category: plugin
  Author: Your Name
  Description: Custom plugin for AgentDB

✓ advanced-scenario (v1.0.0)
  Category: experimental
  Author: AgentDB Team
  Description: Advanced simulation with progress tracking

Uninstalling Plugins

agentdb plugin uninstall my-custom-plugin

Event System

Available Events

// Simulation lifecycle
runner.on('start', (scenario: string, config: AgentDBConfig) => {
  console.log(`Starting ${scenario}...`);
});

runner.on('progress', (progress: ProgressUpdate) => {
  console.log(`Progress: ${progress.percent.toFixed(1)}%`);
});

runner.on('complete', (result: SimulationResult) => {
  console.log(`Completed with recall: ${result.metrics.recall}`);
});

runner.on('error', (error: Error) => {
  console.error(`Error: ${error.message}`);
});

runner.on('cancelled', () => {
  console.log('Simulation cancelled');
});

// Health monitoring
monitor.on('alert', (alert: Alert) => {
  console.warn(`Alert: ${alert.message}`);
});

monitor.on('metrics', (metrics: HealthMetrics) => {
  console.log(`Memory: ${metrics.memory.heapUsed.toFixed(0)}MB`);
});

monitor.on('healing', (action: HealingAction) => {
  console.log(`Self-healing: ${action.type}`);
});

// Registry events
registry.on('scenario-discovered', (scenario: SimulationScenario) => {
  console.log(`Discovered: ${scenario.metadata.name}`);
});

registry.on('plugin-registered', (plugin: SimulationScenario) => {
  console.log(`Registered plugin: ${plugin.metadata.name}`);
});

Custom Event Emitters

class CustomScenario extends EventEmitter implements SimulationScenario {
  async execute(config: AgentDBConfig): Promise<SimulationResult> {
    // Emit custom events
    this.emit('custom-event', { data: 'example' });

    // Emit progress
    for (let i = 0; i < 100; i++) {
      this.emit('progress', {
        iteration: i,
        total: 100,
        percent: (i / 100) * 100
      });

      await this.simulateWork();
    }

    return {
      scenario: this.metadata.id,
      timestamp: new Date(),
      config,
      metrics: { recall: 0.95, latency: 100, throughput: 1000, memoryUsage: 512 },
      insights: [],
      recommendations: []
    };
  }

  private async simulateWork(): Promise<void> {
    await new Promise(resolve => setTimeout(resolve, 10));
  }
}

Code Examples

Example 1: HNSW Optimization Plugin

// ~/.agentdb/plugins/hnsw-optimizer/index.ts
import { SimulationScenario, SimulationResult, AgentDBConfig } from 'agentdb';

export const hnswOptimizer: SimulationScenario = {
  metadata: {
    id: 'hnsw-optimizer',
    name: 'HNSW Optimizer',
    version: '1.0.0',
    category: 'plugin',
    description: 'Find optimal HNSW parameters for your dataset',
    agentdbVersion: '^2.0.0',
    tags: ['hnsw', 'optimization'],
    estimatedDuration: 120000,
    requiredMemoryMB: 2048
  },

  async execute(config: AgentDBConfig): Promise<SimulationResult> {
    const results: Array<{ M: number; recall: number; latency: number }> = [];

    // Test different M values
    for (let M = 8; M <= 64; M += 8) {
      const recall = await this.testHNSW(M, config.hnsw.efConstruction, config.hnsw.efSearch);
      const latency = await this.measureLatency(M, config.hnsw.efSearch);

      results.push({ M, recall, latency });
    }

    // Find optimal M (best recall with latency < threshold)
    const optimal = results
      .filter(r => r.latency < config.monitoring.alertThresholds.latencyMs)
      .sort((a, b) => b.recall - a.recall)[0];

    return {
      scenario: this.metadata.id,
      timestamp: new Date(),
      config,
      metrics: {
        recall: optimal.recall,
        latency: optimal.latency,
        throughput: 1000 / (optimal.latency / 1000),
        memoryUsage: process.memoryUsage().heapUsed / 1024 / 1024,
        optimalM: optimal.M
      },
      insights: [
        `Optimal M found: ${optimal.M}`,
        `Achieves ${(optimal.recall * 100).toFixed(1)}% recall`,
        `Latency: ${optimal.latency.toFixed(2)}ms`
      ],
      recommendations: [
        `Set hnsw.M to ${optimal.M} for best results`,
        `This provides ${((optimal.recall - config.hnsw.M / 100) * 100).toFixed(1)}% better recall`
      ]
    };
  },

  private async testHNSW(M: number, efConstruction: number, efSearch: number): Promise<number> {
    // Implement HNSW testing logic
    return 0.9 + (M / 100) * 0.08; // Simplified
  },

  private async measureLatency(M: number, efSearch: number): Promise<number> {
    // Implement latency measurement
    return 100 + M * 2; // Simplified
  }
};

export default hnswOptimizer;

Example 2: A/B Testing Plugin

// ~/.agentdb/plugins/ab-testing/index.ts
import { SimulationScenario, SimulationResult, AgentDBConfig } from 'agentdb';
import { ReportStore } from 'agentdb/cli/lib/report-store';

export class ABTestingScenario implements SimulationScenario {
  metadata = {
    id: 'ab-testing',
    name: 'A/B Testing',
    version: '1.0.0',
    category: 'plugin' as const,
    description: 'Compare two configurations automatically',
    agentdbVersion: '^2.0.0',
    estimatedDuration: 60000
  };

  async execute(config: AgentDBConfig): Promise<SimulationResult> {
    // Configuration A (current)
    const resultA = await this.runConfiguration(config, 'A');

    // Configuration B (alternative with higher M)
    const configB = { ...config, hnsw: { ...config.hnsw, M: config.hnsw.M + 16 } };
    const resultB = await this.runConfiguration(configB, 'B');

    // Statistical significance test
    const pValue = this.calculatePValue(resultA.recall, resultB.recall);
    const significant = pValue < 0.05;

    const winner = resultB.recall > resultA.recall ? 'B' : 'A';

    return {
      scenario: this.metadata.id,
      timestamp: new Date(),
      config,
      metrics: {
        recall: Math.max(resultA.recall, resultB.recall),
        latency: winner === 'A' ? resultA.latency : resultB.latency,
        throughput: winner === 'A' ? resultA.throughput : resultB.throughput,
        memoryUsage: process.memoryUsage().heapUsed / 1024 / 1024,
        pValue,
        winner: winner === 'A' ? 0 : 1
      },
      insights: [
        `Configuration ${winner} wins with ${significant ? 'significant' : 'insignificant'} improvement`,
        `p-value: ${pValue.toFixed(4)}`,
        `Recall improvement: ${((resultB.recall - resultA.recall) * 100).toFixed(2)}%`
      ],
      recommendations: winner === 'B' ? [
        `Switch to configuration B (M=${configB.hnsw.M})`,
        `Expected improvement: ${((resultB.recall - resultA.recall) * 100).toFixed(1)}%`
      ] : [
        'Current configuration is optimal'
      ]
    };
  }

  private async runConfiguration(config: AgentDBConfig, variant: string): Promise<any> {
    // Run simulation with configuration
    // (simplified example)
    return {
      recall: 0.92 + Math.random() * 0.05,
      latency: 100 + Math.random() * 50,
      throughput: 1000
    };
  }

  private calculatePValue(recallA: number, recallB: number): number {
    // Simplified p-value calculation
    const diff = Math.abs(recallB - recallA);
    return Math.max(0.01, 0.5 - diff * 2);
  }
}

export default new ABTestingScenario();

Testing Plugins

Unit Tests

// ~/.agentdb/plugins/my-plugin/tests/index.test.ts
import { describe, it, expect } from 'vitest';
import myPlugin from '../index';

describe('My Plugin', () => {
  it('should have valid metadata', () => {
    expect(myPlugin.metadata.id).toBe('my-plugin');
    expect(myPlugin.metadata.version).toMatch(/^\d+\.\d+\.\d+$/);
  });

  it('should execute successfully', async () => {
    const config = createMockConfig();
    const result = await myPlugin.execute(config);

    expect(result.metrics.recall).toBeGreaterThan(0);
    expect(result.metrics.latency).toBeGreaterThan(0);
  });

  it('should validate configuration', () => {
    const config = createMockConfig();
    const validation = myPlugin.validate!(config);

    expect(validation.valid).toBe(true);
  });
});

function createMockConfig(): any {
  return {
    profile: 'production',
    hnsw: { M: 32, efConstruction: 200, efSearch: 100 },
    // ... other fields
  };
}

Publishing Plugins

npm Package

// package.json
{
  "name": "agentdb-plugin-myname",
  "version": "1.0.0",
  "description": "My custom AgentDB plugin",
  "main": "dist/index.js",
  "types": "dist/index.d.ts",
  "keywords": ["agentdb", "plugin", "simulation"],
  "peerDependencies": {
    "agentdb": "^2.0.0"
  },
  "devDependencies": {
    "typescript": "^5.0.0",
    "vitest": "^1.0.0"
  },
  "scripts": {
    "build": "tsc",
    "test": "vitest"
  }
}

Publishing

npm publish

Installing Published Plugin

npm install -g agentdb-plugin-myname
agentdb plugin install agentdb-plugin-myname

Document Version: 1.0 Last Updated: 2025-11-30 Maintainer: AgentDB Team