Skip to main content
Glama
enkryptai

Enkrypt AI Secure MCP Gateway

Official
by enkryptai
provider_loader.py4.15 kB
"""Dynamic provider loader.""" from __future__ import annotations import importlib from typing import Any from secure_mcp_gateway.error_handling import error_logger from secure_mcp_gateway.exceptions import ( ErrorCode, ErrorContext, create_configuration_error, ) from secure_mcp_gateway.utils import logger def load_provider_class(class_path: str) -> type: """ Dynamically load a provider class from its module path. Args: class_path: Full path to class (e.g., "module.submodule.ClassName") Returns: The provider class Raises: ImportError: If module or class cannot be found Example: >>> cls = load_provider_class("secure_mcp_gateway.plugins.guardrails.example_providers.OpenAIGuardrailProvider") >>> provider = cls(api_key="xxx") """ try: # Split the class path into module and class name module_path, class_name = class_path.rsplit(".", 1) # Import the module module = importlib.import_module(module_path) # Get the class from the module provider_class = getattr(module, class_name) return provider_class except (ValueError, ImportError, AttributeError) as e: raise ImportError(f"Cannot load provider class '{class_path}': {e}") from e def create_provider_from_config( provider_config: dict[str, Any], plugin_type: str = "guardrail" ) -> Any: """ Create a provider instance from configuration. Args: provider_config: Provider configuration dict with: - class: Full class path (required) - config: Provider-specific config (optional) plugin_type: Type of plugin (guardrail, auth, telemetry) Returns: Provider instance Example Config: { "name": "my-openai-provider", "class": "secure_mcp_gateway.plugins.guardrails.example_providers.OpenAIGuardrailProvider", "config": { "api_key": "sk-xxx" } } """ provider_name = provider_config.get("name", "unknown") class_path = provider_config.get("class") config = provider_config.get("config", {}) if not class_path: context = ErrorContext( operation="provider_loader.missing_class", additional_context={ "provider_name": provider_name, "plugin_type": plugin_type, }, ) err = create_configuration_error( code=ErrorCode.CONFIG_MISSING_REQUIRED, message=f"Provider '{provider_name}' missing 'class' field", context=context, ) error_logger.log_error(err) raise err try: # Load the provider class provider_class = load_provider_class(class_path) # Create instance with config # Try different initialization patterns try: # Pattern 1: Pass entire config dict provider = provider_class(**config) except TypeError: try: # Pattern 2: Pass config as single argument provider = provider_class(config) except TypeError: # Pattern 3: No config needed provider = provider_class() logger.info( f"✓ Loaded {plugin_type} provider: {provider_name} ({provider_class.__name__})" ) return provider except Exception as e: logger.error(f"✗ Failed to load provider '{provider_name}': {e}") context = ErrorContext( operation="provider_loader.load_provider", additional_context={ "provider_name": provider_name, "plugin_type": plugin_type, "class_path": class_path, }, ) err = create_configuration_error( code=ErrorCode.CONFIG_PROVIDER_ERROR, message=f"Cannot load provider '{provider_name}'", context=context, cause=e, ) error_logger.log_error(err) raise err __all__ = [ "load_provider_class", "create_provider_from_config", ]

Latest Blog Posts

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/enkryptai/secure-mcp-gateway'

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