salmanabjam/deepvision-prompt-builder
0
1"""2Base Plugin Class3 4Defines the interface that all plugins must implement.5"""6 7from abc import ABC, abstractmethod8from dataclasses import dataclass9from typing import Dict, Any, Optional, List10from pathlib import Path11from PIL import Image12import numpy as np13from loguru import logger14 15 16@dataclass17class PluginMetadata:18 """Metadata for a plugin."""19 20 name: str21 version: str22 description: str23 author: str24 requires: List[str] = None # Required dependencies25 category: str = "general" # Plugin category26 enabled: bool = True27 priority: int = 50 # Execution priority (lower = earlier)28 29 def __post_init__(self):30 if self.requires is None:31 self.requires = []32 33 34class BasePlugin(ABC):35 """36 Base class for all DeepVision plugins.37 38 All plugins must inherit from this class and implement39 the analyze() method.40 """41 42 def __init__(self):43 """Initialize plugin."""44 self._metadata: Optional[PluginMetadata] = None45 self._initialized = False46 self._enabled = True47 logger.debug(f"Plugin {self.__class__.__name__} created")48 49 @property50 @abstractmethod51 def metadata(self) -> PluginMetadata:52 """53 Return plugin metadata.54 55 Returns:56 PluginMetadata instance57 """58 pass59 60 @abstractmethod61 def initialize(self) -> None:62 """63 Initialize the plugin.64 65 This method is called when the plugin is loaded.66 Use it to load models, initialize resources, etc.67 """68 pass69 70 @abstractmethod71 def analyze(72 self,73 media: Any,74 media_path: Path75 ) -> Dict[str, Any]:76 """77 Analyze media and return results.78 79 Args:80 media: Processed media (PIL Image or numpy array)81 media_path: Path to the media file82 83 Returns:84 Dictionary with analysis results85 """86 pass87 88 def cleanup(self) -> None:89 """90 Clean up resources when plugin is unloaded.91 92 Override this method to release resources like93 model memory, file handles, etc.94 """95 logger.debug(f"Cleaning up plugin {self.metadata.name}")96 97 def validate_input(self, media: Any) -> bool:98 """99 Validate input media.100 101 Args:102 media: Media to validate103 104 Returns:105 True if valid, False otherwise106 """107 if isinstance(media, Image.Image):108 return True109 elif isinstance(media, np.ndarray):110 return True111 else:112 logger.warning(113 f"Plugin {self.metadata.name} received unsupported media type: "114 f"{type(media)}"115 )116 return False117 118 def get_config(self) -> Dict[str, Any]:119 """120 Get plugin configuration.121 122 Returns:123 Configuration dictionary124 """125 return {126 "name": self.metadata.name,127 "version": self.metadata.version,128 "enabled": self._enabled,129 "initialized": self._initialized,130 }131 132 def set_enabled(self, enabled: bool) -> None:133 """134 Enable or disable the plugin.135 136 Args:137 enabled: True to enable, False to disable138 """139 self._enabled = enabled140 logger.info(141 f"Plugin {self.metadata.name} "142 f"{'enabled' if enabled else 'disabled'}"143 )144 145 def is_enabled(self) -> bool:146 """147 Check if plugin is enabled.148 149 Returns:150 True if enabled151 """152 return self._enabled153 154 def is_initialized(self) -> bool:155 """156 Check if plugin is initialized.157 158 Returns:159 True if initialized160 """161 return self._initialized162 163 def __repr__(self) -> str:164 """String representation."""165 return (166 f"{self.__class__.__name__}("167 f"name={self.metadata.name}, "168 f"version={self.metadata.version}, "169 f"enabled={self._enabled})"170 )171 