UNPKG

@simonecoelhosfo/optimizely-mcp-server

Version:

Optimizely MCP Server for AI assistants with integrated CLI tools

123 lines 7.4 kB
/** * Get Project Data Tool - Individual Module * @description Retrieves comprehensive project data with aggregation * @since 2025-08-04 * @author Tool Modularization Team * * Migration Status: COMPLETED * Original Method: OptimizelyMCPTools.getProjectData * Complexity: LOW * Dependencies: storage.query, logger, errorMapper, cacheManager */ /** * Creates the Get Project Data tool with injected dependencies * @param deps - Injected dependencies (storage, logger, errorMapper, etc.) * @returns Tool definition with handler */ export function createGetProjectDataTool(deps) { return { name: 'get_project_data', requiresCache: true, category: 'discovery', description: 'Retrieves comprehensive project data with aggregation', handler: async (args) => { try { const { project_id: projectId, options = {} } = args; deps.logger.debug({ projectId, options }, 'OptimizelyMCPTools.getProjectData: Getting comprehensive project data from cache'); // Set defaults: if no specific include options are provided, include everything const defaults = { include_flags: true, include_experiments: true, include_audiences: true, include_attributes: true, include_events: true, include_environments: true, include_rulesets: true }; // Only use defaults if no include options were explicitly provided const hasAnyIncludes = Object.keys(options).some(key => key.startsWith('include_')); const finalOptions = hasAnyIncludes ? options : { ...defaults, ...options }; if (!deps.cacheManager) { throw deps.errorMapper.toMCPError(new Error("Cache manager not initialized"), { operation: 'Get project data' }); } // Build result object with requested entities from cache const result = { result: "success", metadata: { operation: "get_project_data", project_id: projectId, operation_successful: true, timestamp: new Date().toISOString(), data_source: "cache" } }; // Get project details first const projectQuery = await deps.storage.query('SELECT * FROM projects WHERE id = ?', [projectId]); if (!projectQuery.length) { throw deps.errorMapper.toMCPError(new Error(`Project ${projectId} not found in cache`), { operation: 'Get project data', metadata: { projectId } }); } result.project = projectQuery[0]; const isFeatureExperimentation = result.project.platform === 'custom' || result.project.is_flags_enabled; // Include requested entities using efficient cache queries if (finalOptions.include_flags) { result.flags = await deps.storage.query('SELECT id, key, name, description, archived, created_time, updated_time FROM flags WHERE project_id = ? AND archived = 0 ORDER BY updated_time DESC', [projectId]); } if (finalOptions.include_experiments) { if (isFeatureExperimentation) { // For Feature Experimentation, get A/B test rulesets result.experiments = await deps.storage.query('SELECT flag_key, environment_key, enabled, archived, rules_summary FROM flag_environments WHERE project_id = ? AND (data_json LIKE ? OR data_json LIKE ?) ORDER BY environment_key', [projectId, '%"type":"a/b_test"%', '%"type":"experiment"%']); } else { // For Web Experimentation, get standalone experiments result.experiments = await deps.storage.query('SELECT id, key, name, description, status, archived, created_time, updated_time FROM experiments WHERE project_id = ? AND archived = 0 ORDER BY updated_time DESC', [projectId]); } } if (finalOptions.include_audiences) { result.audiences = await deps.storage.query('SELECT id, name, description, conditions, archived, created_time, last_modified FROM audiences WHERE project_id = ? AND archived = 0 ORDER BY last_modified DESC', [projectId]); } if (finalOptions.include_attributes) { result.attributes = await deps.storage.query('SELECT id, key, name, condition_type, archived, last_modified FROM attributes WHERE project_id = ? AND archived = 0 ORDER BY last_modified DESC', [projectId]); } if (finalOptions.include_events) { result.events = await deps.storage.query('SELECT id, key, name, description, event_type, category, archived, created_time FROM events WHERE project_id = ? AND archived = 0 ORDER BY created_time DESC', [projectId]); } if (finalOptions.include_environments) { result.environments = await deps.storage.query('SELECT key, name, is_primary, priority, archived FROM environments WHERE project_id = ? ORDER BY priority, key', [projectId]); } if (finalOptions.include_rulesets && isFeatureExperimentation) { result.rulesets = await deps.storage.query('SELECT flag_key, environment_key, enabled, archived, rules_summary FROM flag_environments WHERE project_id = ? ORDER BY flag_key, environment_key', [projectId]); } // Add summary counts result.summary = { total_entities: 0, platform_type: isFeatureExperimentation ? 'Feature Experimentation' : 'Web Experimentation' }; // Count entities that were included ['flags', 'experiments', 'audiences', 'attributes', 'events', 'environments', 'rulesets'].forEach(entityType => { if (result[entityType]) { result.summary.total_entities += result[entityType].length; result.summary[`${entityType}_count`] = result[entityType].length; } }); deps.logger.debug({ projectId, totalEntities: result.summary.total_entities, includedTypes: Object.keys(result).filter(key => Array.isArray(result[key])) }, 'OptimizelyMCPTools.getProjectData: Successfully retrieved project data from cache'); return result; } catch (error) { deps.logger.error({ projectId: args.project_id, error: error.message, stack: error.stack }, 'OptimizelyMCPTools.getProjectData: Failed to get project data'); throw deps.errorMapper.toMCPError(error, 'Failed to get comprehensive project data'); } } }; } //# sourceMappingURL=GetProjectData.js.map