quantum-cli-core
Version:
Quantum CLI Core - Multi-LLM Collaboration System
282 lines • 10.7 kB
JavaScript
/**
* @license
* Copyright 2025 Google LLC
* SPDX-License-Identifier: Apache-2.0
*/
import { UncertaintyLevel } from '../types.js';
export class AutoTriggerSystem {
config;
constructor(config) {
this.config = config;
}
updateConfig(newConfig) {
this.config = { ...this.config, ...newConfig };
}
shouldTriggerVerification(query, uncertaintyResult, context) {
// Check cost limitation first
if (this.isOverCostLimit()) {
return {
shouldVerify: false,
shouldCompare: false,
reason: 'monthly_cost_limit_exceeded',
costImpact: 'high',
confidence: 1.0,
};
}
// Check if domain is in skip list
if (this.shouldSkipDomain(context?.domain)) {
return {
shouldVerify: false,
shouldCompare: false,
reason: 'domain_in_skip_list',
costImpact: 'low',
confidence: 0.9,
};
}
// Force verification for priority domains
if (this.isPriorityDomain(context?.domain)) {
return {
shouldVerify: true,
shouldCompare: uncertaintyResult.level === UncertaintyLevel.CRITICAL,
reason: 'priority_domain_always_verify',
costImpact: 'medium',
confidence: 1.0,
};
}
// Calculate query complexity score
const queryComplexityScore = this.calculateQueryComplexity(query);
// Apply aggressiveness modifier
const aggressivenessModifier = this.getAggressivenessModifier();
// Calculate final decision score
const decisionScore = this.calculateDecisionScore(uncertaintyResult, queryComplexityScore, aggressivenessModifier, context);
// Determine actions based on thresholds
const shouldCompare = this.shouldTriggerCompare(decisionScore, uncertaintyResult.level);
const shouldVerify = shouldCompare ||
this.shouldTriggerVerify(decisionScore, uncertaintyResult.level);
// Cost awareness check
if (this.config.userPreferences.enableCostAwareMode &&
this.isNearCostLimit()) {
if (shouldCompare &&
uncertaintyResult.level !== UncertaintyLevel.CRITICAL) {
return {
shouldVerify,
shouldCompare: false,
reason: 'cost_aware_downgrade_compare_to_verify',
costImpact: 'medium',
confidence: 0.7,
};
}
if (shouldVerify && uncertaintyResult.level === UncertaintyLevel.LOW) {
return {
shouldVerify: false,
shouldCompare: false,
reason: 'cost_aware_skip_low_uncertainty',
costImpact: 'low',
confidence: 0.6,
};
}
}
return {
shouldVerify,
shouldCompare,
reason: this.getDecisionReason(shouldVerify, shouldCompare, decisionScore, uncertaintyResult),
costImpact: this.calculateCostImpact(shouldVerify, shouldCompare),
confidence: this.calculateConfidence(decisionScore, uncertaintyResult),
};
}
calculateQueryComplexity(query) {
const wordCount = query.split(/\s+/).length;
const { shortQuery, longQuery, complexityMultiplier } = this.config.queryLengthFactors;
let lengthScore = 0;
if (wordCount <= shortQuery) {
lengthScore = 0.2; // Short queries might need less verification
}
else if (wordCount >= longQuery) {
lengthScore = 0.8; // Long queries might be more complex
}
else {
// Linear interpolation between short and long
lengthScore =
0.2 + ((wordCount - shortQuery) / (longQuery - shortQuery)) * 0.6;
}
// Check for complexity indicators in the query itself
const complexityIndicators = [
/multiple|various|different|compare|analyze/i,
/security|production|critical|important/i,
/how to|best practice|recommend|suggest/i,
/\?.*\?/, // Multiple questions
/step.?by.?step|detailed|comprehensive/i,
];
let complexityBonus = 0;
for (const indicator of complexityIndicators) {
if (indicator.test(query)) {
complexityBonus += 0.1;
}
}
return Math.min((lengthScore + complexityBonus) * complexityMultiplier, 1.0);
}
getAggressivenessModifier() {
switch (this.config.userPreferences.aggressiveness) {
case 'conservative':
return 0.7; // Higher threshold for triggering
case 'balanced':
return 1.0; // Normal thresholds
case 'aggressive':
return 1.3; // Lower threshold for triggering
default:
return 1.0;
}
}
calculateDecisionScore(uncertaintyResult, queryComplexity, aggressivenessModifier, context) {
// Base score from uncertainty level
let baseScore = 0;
switch (uncertaintyResult.level) {
case UncertaintyLevel.CRITICAL:
baseScore = 1.0;
break;
case UncertaintyLevel.HIGH:
baseScore = 0.8;
break;
case UncertaintyLevel.MEDIUM:
baseScore = 0.5;
break;
case UncertaintyLevel.LOW:
baseScore = 0.2;
break;
default: {
baseScore = 0.1;
break;
}
}
// Factor in query complexity (20% weight)
const complexityFactor = queryComplexity * 0.2;
// Factor in context criticality (10% weight)
let contextFactor = 0;
if (context?.type) {
contextFactor = 0.1; // Any specific context adds some weight
}
// Apply aggressiveness modifier
const finalScore = (baseScore + complexityFactor + contextFactor) * aggressivenessModifier;
return Math.min(finalScore, 1.0);
}
shouldTriggerVerify(score, level) {
// Always verify critical unless cost-limited
if (level === UncertaintyLevel.CRITICAL) {
return true;
}
// Use score-based threshold for other levels
return score >= 0.4; // Configurable threshold
}
shouldTriggerCompare(score, level) {
// Always compare critical
if (level === UncertaintyLevel.CRITICAL) {
return true;
}
// High threshold for comparison (more expensive)
return score >= 0.7;
}
isOverCostLimit() {
const { monthlyLimit, currentUsage } = this.config.costLimitation;
return currentUsage >= monthlyLimit;
}
isNearCostLimit() {
const { monthlyLimit, currentUsage, warningThreshold } = this.config.costLimitation;
return currentUsage >= monthlyLimit * warningThreshold;
}
shouldSkipDomain(domain) {
if (!domain)
return false;
return this.config.userPreferences.skipDomains.some((skipDomain) => domain.toLowerCase().includes(skipDomain.toLowerCase()));
}
isPriorityDomain(domain) {
if (!domain)
return false;
return this.config.userPreferences.priorityDomains.some((priorityDomain) => domain.toLowerCase().includes(priorityDomain.toLowerCase()));
}
getDecisionReason(shouldVerify, shouldCompare, score, uncertaintyResult) {
if (shouldCompare) {
return `high_uncertainty_score_${score.toFixed(2)}_level_${uncertaintyResult.level}`;
}
if (shouldVerify) {
return `medium_uncertainty_score_${score.toFixed(2)}_level_${uncertaintyResult.level}`;
}
return `low_uncertainty_score_${score.toFixed(2)}_level_${uncertaintyResult.level}`;
}
calculateCostImpact(shouldVerify, shouldCompare) {
if (shouldCompare) {
return 'high'; // Multiple API calls
}
if (shouldVerify) {
return 'medium'; // One additional API call
}
return 'low'; // No additional calls
}
calculateConfidence(score, uncertaintyResult) {
// Higher confidence for extreme scores (very high or very low)
const extremeScore = Math.abs(score - 0.5) * 2; // 0-1 range
// Base confidence from uncertainty level clarity
let baseConfidence = 0.5;
if (uncertaintyResult.level === UncertaintyLevel.CRITICAL ||
uncertaintyResult.level === UncertaintyLevel.LOW) {
baseConfidence = 0.8; // Clear cases
}
return Math.min(baseConfidence + extremeScore * 0.2, 1.0);
}
// Utility methods for external usage tracking
incrementUsage() {
this.config.costLimitation.currentUsage += 1;
}
getRemainingCalls() {
return Math.max(0, this.config.costLimitation.monthlyLimit -
this.config.costLimitation.currentUsage);
}
getCostStatus() {
const { monthlyLimit, currentUsage, warningThreshold } = this.config.costLimitation;
const percentage = currentUsage / monthlyLimit;
let status;
if (percentage >= 1.0) {
status = 'exceeded';
}
else if (percentage >= warningThreshold) {
status = 'critical';
}
else if (percentage >= 0.7) {
status = 'warning';
}
else {
status = 'safe';
}
return {
usage: currentUsage,
limit: monthlyLimit,
percentage,
status,
};
}
}
// Default configuration factory
export function createDefaultAutoTriggerConfig() {
return {
uncertaintyThresholds: {
verify: UncertaintyLevel.MEDIUM,
compare: UncertaintyLevel.HIGH,
},
queryLengthFactors: {
shortQuery: 10, // words
longQuery: 50, // words
complexityMultiplier: 1.2,
},
costLimitation: {
monthlyLimit: 1000, // API calls per month
currentUsage: 0,
warningThreshold: 0.8, // 80%
},
userPreferences: {
aggressiveness: 'balanced',
priorityDomains: ['security', 'production', 'critical', 'financial'],
skipDomains: ['tutorial', 'example', 'demo'],
enableCostAwareMode: true,
},
};
}
//# sourceMappingURL=auto-trigger.js.map