Files
antigravity-claude-proxy/src/config.js

120 lines
3.9 KiB
JavaScript

import fs from 'fs';
import path from 'path';
import os from 'os';
import { logger } from './utils/logger.js';
// Default config
const DEFAULT_CONFIG = {
apiKey: '',
webuiPassword: '',
debug: false,
logLevel: 'info',
maxRetries: 5,
retryBaseMs: 1000,
retryMaxMs: 30000,
persistTokenCache: false,
defaultCooldownMs: 10000, // 10 seconds
maxWaitBeforeErrorMs: 120000, // 2 minutes
maxAccounts: 10, // Maximum number of accounts allowed
modelMapping: {},
// Account selection strategy configuration
accountSelection: {
strategy: 'hybrid', // 'sticky' | 'round-robin' | 'hybrid'
// Hybrid strategy tuning (optional - sensible defaults)
healthScore: {
initial: 70, // Starting score for new accounts
successReward: 1, // Points on successful request
rateLimitPenalty: -10, // Points on rate limit
failurePenalty: -20, // Points on other failures
recoveryPerHour: 2, // Passive recovery rate
minUsable: 50, // Minimum score to be selected
maxScore: 100 // Maximum score cap
},
tokenBucket: {
maxTokens: 50, // Maximum token capacity
tokensPerMinute: 6, // Regeneration rate
initialTokens: 50 // Starting tokens
},
quota: {
lowThreshold: 0.10, // 10% - reduce score
criticalThreshold: 0.05, // 5% - exclude from candidates
staleMs: 300000 // 5 min - max age of quota data to trust
}
}
};
// Config locations
const HOME_DIR = os.homedir();
const CONFIG_DIR = path.join(HOME_DIR, '.config', 'antigravity-proxy');
const CONFIG_FILE = path.join(CONFIG_DIR, 'config.json');
// Ensure config dir exists
if (!fs.existsSync(CONFIG_DIR)) {
try {
fs.mkdirSync(CONFIG_DIR, { recursive: true });
} catch (err) {
// Ignore
}
}
// Load config
let config = { ...DEFAULT_CONFIG };
function loadConfig() {
try {
// Env vars take precedence for initial defaults, but file overrides them if present?
// Usually Env > File > Default.
if (fs.existsSync(CONFIG_FILE)) {
const fileContent = fs.readFileSync(CONFIG_FILE, 'utf8');
const userConfig = JSON.parse(fileContent);
config = { ...DEFAULT_CONFIG, ...userConfig };
} else {
// Try looking in current dir for config.json as fallback
const localConfigPath = path.resolve('config.json');
if (fs.existsSync(localConfigPath)) {
const fileContent = fs.readFileSync(localConfigPath, 'utf8');
const userConfig = JSON.parse(fileContent);
config = { ...DEFAULT_CONFIG, ...userConfig };
}
}
// Environment overrides
if (process.env.API_KEY) config.apiKey = process.env.API_KEY;
if (process.env.WEBUI_PASSWORD) config.webuiPassword = process.env.WEBUI_PASSWORD;
if (process.env.DEBUG === 'true') config.debug = true;
} catch (error) {
logger.error('[Config] Error loading config:', error);
}
}
// Initial load
loadConfig();
export function getPublicConfig() {
// Create a deep copy and redact sensitive fields
const publicConfig = JSON.parse(JSON.stringify(config));
// Redact sensitive values
if (publicConfig.webuiPassword) publicConfig.webuiPassword = '********';
if (publicConfig.apiKey) publicConfig.apiKey = '********';
return publicConfig;
}
export function saveConfig(updates) {
try {
// Apply updates
config = { ...config, ...updates };
// Save to disk
fs.writeFileSync(CONFIG_FILE, JSON.stringify(config, null, 2), 'utf8');
return true;
} catch (error) {
logger.error('[Config] Failed to save config:', error);
return false;
}
}
export { config };