Skip to main content
Glama

Createve.AI Nexus

by spgoodman
executor.pyβ€’6.35 kB
"""API executor for executing API endpoints.""" import inspect import logging from typing import Dict, Any, List, Tuple, Optional from ..models import APIError, APIErrorCode from .converter import TypeConverter class APIExecutor: """Executor for API endpoints.""" def __init__(self, apis: Dict[str, Dict[str, Any]], logger: logging.Logger): self.apis = apis self.logger = logger self.converter = TypeConverter(logger) async def execute_api(self, api_path: str, data: dict) -> dict: """Execute API endpoint.""" try: # Find API api_info = self.apis.get(api_path) if not api_info: raise APIError( APIErrorCode.NOT_FOUND, f"API endpoint {api_path} not found" ) # Create instance cls = api_info['class'] instance = cls() # Get input types input_types = self._get_input_types(cls) # Get function to execute function_name = getattr(cls, 'FUNCTION') func = getattr(instance, function_name) # Prepare arguments args, kwargs = await self._prepare_arguments(data, input_types) # Execute function try: result = func(*args, **kwargs) # If result is tuple, convert to dict using RETURN_NAMES if isinstance(result, tuple): result_dict = {} return_names = getattr(cls, 'RETURN_NAMES', None) for i, value in enumerate(result): if return_names and i < len(return_names): name = return_names[i] else: name = f"output_{i}" result_dict[name] = value result = result_dict # Process result processed_result = await self._process_result(result, cls) return processed_result except Exception as e: self.logger.error(f"Error executing API {api_path}: {str(e)}") raise APIError( APIErrorCode.API_ERROR, f"Error executing API: {str(e)}" ) except APIError: raise except Exception as e: self.logger.error(f"Error processing API {api_path}: {str(e)}") raise APIError( APIErrorCode.API_ERROR, f"Error processing API: {str(e)}" ) def _get_input_types(self, cls) -> Dict[str, Dict[str, Any]]: """Get input types for class.""" try: input_types_method = getattr(cls, 'INPUT_TYPES') if callable(input_types_method): input_types = input_types_method() else: input_types = input_types_method return input_types except Exception as e: self.logger.error(f"Error getting input types: {str(e)}") return {} async def _prepare_arguments(self, data: dict, input_types: Dict[str, Dict[str, Any]]) -> Tuple[List[Any], Dict[str, Any]]: """Prepare arguments for function call.""" args = [] kwargs = {} # Process required arguments for field, type_info in input_types.get('required', {}).items(): if field not in data: raise APIError( APIErrorCode.INVALID_INPUT, f"Missing required field: {field}" ) value = data[field] # Convert if needed if isinstance(type_info, tuple) and len(type_info) > 0: type_name = type_info[0] # Check if value is base64 string for file types if type_name in ["IMAGE", "VIDEO", "FILE"] and isinstance(value, str): value = await self.converter.convert_from_base64(value, type_name) kwargs[field] = value # Process optional arguments for field, type_info in input_types.get('optional', {}).items(): if field in data: value = data[field] # Convert if needed if isinstance(type_info, tuple) and len(type_info) > 0: type_name = type_info[0] # Check if value is base64 string for file types if type_name in ["IMAGE", "VIDEO", "FILE"] and isinstance(value, str): value = await self.converter.convert_from_base64(value, type_name) kwargs[field] = value return args, kwargs async def _process_result(self, result: Any, cls) -> dict: """Process result of function call.""" # If result is already a dict, process each value if isinstance(result, dict): processed_result = {} # Get return types if available return_types = getattr(cls, 'RETURN_TYPES', None) return_names = getattr(cls, 'RETURN_NAMES', None) for key, value in result.items(): # Find type for this key type_name = None if return_names and return_types: try: index = return_names.index(key) if index < len(return_types): type_name = return_types[index] except ValueError: pass # Convert if needed if type_name in ["IMAGE", "VIDEO", "FILE"]: processed_result[key] = await self.converter.convert_to_base64(value, type_name) else: processed_result[key] = value return processed_result # Otherwise, return result as is return result

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/spgoodman/createveai-nexus-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server