Class PluginManager

java.lang.Object
cloud.opencode.base.classloader.plugin.PluginManager
All Implemented Interfaces:
AutoCloseable

public class PluginManager extends Object implements AutoCloseable
Plugin lifecycle manager - Manages plugin discovery, loading, starting, stopping and unloading 插件生命周期管理器 - 管理插件的发现、加载、启动、停止和卸载

Provides a complete plugin lifecycle management framework built on top of IsoClassLoader for class isolation. Plugins are discovered from JAR files containing META-INF/opencode/plugin.properties descriptors.

基于 IsoClassLoader 提供完整的插件生命周期管理框架,实现类隔离。 通过包含 META-INF/opencode/plugin.properties 描述符的 JAR 文件发现插件。

Lifecycle | 生命周期:

discover → load → start → stop → unload
                                 \               /
                                  ← reload ←

Usage Examples | 使用示例:

try (PluginManager manager = PluginManager.builder()
        .pluginDir(Path.of("/plugins"))
        .leakDetection(LeakDetection.SIMPLE)
        .build()) {

    List<PluginDescriptor> descriptors = manager.discoverPlugins();
    for (PluginDescriptor desc : descriptors) {
        manager.load(desc.id());
        manager.start(desc.id());
    }
    // ... use plugins ...
} // auto-closes all plugins

Security | 安全性:

  • Thread-safe: Yes (ConcurrentHashMap + synchronized transitions) - 线程安全: 是 (ConcurrentHashMap + 同步状态转换)
  • Null-safe: Yes - 空值安全: 是
Since:
JDK 25, opencode-base-classloader V1.0.3
Author:
Leon Soo www.LeonSoo.com
See Also:
  • Method Details

    • builder

      public static PluginManager.Builder builder()
      Create a new Builder for PluginManager 创建 PluginManager 的新 Builder
      Returns:
      a new builder instance | 新的构建器实例
    • discoverPlugins

      public List<PluginDescriptor> discoverPlugins()
      Discover plugins by scanning the plugin directory for JARs containing META-INF/opencode/plugin.properties 通过扫描插件目录中包含 META-INF/opencode/plugin.properties 的 JAR 来发现插件
      Returns:
      list of discovered plugin descriptors | 发现的插件描述符列表
      Throws:
      OpenClassLoaderException - if the plugin directory cannot be read | 当无法读取插件目录时
      IllegalStateException - if this manager is closed | 当管理器已关闭时
    • load

      public PluginHandle load(String pluginId)
      Load a discovered plugin: create an isolated ClassLoader and instantiate the Plugin 加载已发现的插件:创建隔离的 ClassLoader 并实例化 Plugin

      Concurrency note: This method uses atomic compute() on the internal plugin map, which may briefly block concurrent load() calls for the same pluginId while the ClassLoader is being created. Calls for different pluginIds are not affected.

      并发说明:此方法对内部插件 map 使用原子 compute() 操作, 在创建 ClassLoader 期间可能短暂阻塞对同一 pluginId 的并发 load() 调用。 不同 pluginId 的调用不受影响。

      Parameters:
      pluginId - the plugin identifier | 插件标识符
      Returns:
      the plugin handle | 插件句柄
      Throws:
      OpenClassLoaderException - if the plugin is not discovered, already loaded, or loading fails | 当插件未发现、已加载或加载失败时
      IllegalStateException - if this manager is closed | 当管理器已关闭时
    • start

      public void start(String pluginId)
      Start a loaded plugin by calling Plugin.onStart(PluginContext) 通过调用 Plugin.onStart(PluginContext) 启动已加载的插件
      Parameters:
      pluginId - the plugin identifier | 插件标识符
      Throws:
      OpenClassLoaderException - if the plugin is not loaded or start fails | 当插件未加载或启动失败时
      IllegalStateException - if this manager is closed | 当管理器已关闭时
    • stop

      public void stop(String pluginId)
      Stop a running plugin by calling Plugin.onStop() 通过调用 Plugin.onStop() 停止运行中的插件
      Parameters:
      pluginId - the plugin identifier | 插件标识符
      Throws:
      OpenClassLoaderException - if the plugin is not started or stop fails | 当插件未启动或停止失败时
      IllegalStateException - if this manager is closed | 当管理器已关闭时
    • unload

      public void unload(String pluginId)
      Unload a plugin: stop if running, then close its ClassLoader 卸载插件:如果正在运行则停止,然后关闭其 ClassLoader
      Parameters:
      pluginId - the plugin identifier | 插件标识符
      Throws:
      OpenClassLoaderException - if the plugin is not found | 当未找到插件时
      IllegalStateException - if this manager is closed | 当管理器已关闭时
    • reload

      public PluginHandle reload(String pluginId)
      Reload a plugin: unload, then load and start 重新加载插件:卸载,然后加载并启动
      Parameters:
      pluginId - the plugin identifier | 插件标识符
      Returns:
      the new plugin handle | 新的插件句柄
      Throws:
      OpenClassLoaderException - if reload fails | 当重新加载失败时
      IllegalStateException - if this manager is closed | 当管理器已关闭时
    • getPlugin

      public Optional<PluginHandle> getPlugin(String pluginId)
      Get a plugin handle by id 通过 ID 获取插件句柄
      Parameters:
      pluginId - the plugin identifier | 插件标识符
      Returns:
      optional plugin handle | 可选的插件句柄
    • getPlugins

      public Map<String, PluginHandle> getPlugins()
      Get all loaded plugin handles 获取所有已加载的插件句柄
      Returns:
      unmodifiable map of plugin id to handle | 不可修改的插件 ID 到句柄的映射
    • close

      public void close()
      Close this manager, unloading all plugins 关闭此管理器,卸载所有插件
      Specified by:
      close in interface AutoCloseable