From 3875251d9725cd6ed365f641a1f5a6b3fd01bfdf Mon Sep 17 00:00:00 2001 From: John Niang Date: Mon, 1 Jul 2024 15:31:17 +0800 Subject: [PATCH] Allow plugin to listen the event the plugin has started (#6234) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit #### What type of PR is this? /kind feature /area core /milestone 2.17.x #### What this PR does / why we need it: This PR add support for allowing plugin to listen the event that the plugin has started. Below is an example of listening the event in plugin: ```java @EventListener void onPluginStartedEvent(PluginStartedEvent event) { // do something. } ``` See https://github.com/halo-dev/halo/issues/5339#issuecomment-2199220068 for more. #### Which issue(s) this PR fixes: Fixes https://github.com/halo-dev/halo/issues/5339#issuecomment-2199220068 #### Special notes for your reviewer: 1. Create a plugin, add the listener above and write some logs 2. Build and install the plugin 3. Start plugin and see the logs you wrote #### Does this PR introduce a user-facing change? ```release-note 支持在插件中监听已启动事件 ``` --- .../app/plugin/event/PluginStartedEvent.java | 17 +++++++++ .../halo/app/plugin/HaloPluginManager.java | 33 +++++++++++++++++ .../event/HaloPluginStateChangedEvent.java | 36 ------------------- 3 files changed, 50 insertions(+), 36 deletions(-) create mode 100644 api/src/main/java/run/halo/app/plugin/event/PluginStartedEvent.java delete mode 100644 application/src/main/java/run/halo/app/plugin/event/HaloPluginStateChangedEvent.java diff --git a/api/src/main/java/run/halo/app/plugin/event/PluginStartedEvent.java b/api/src/main/java/run/halo/app/plugin/event/PluginStartedEvent.java new file mode 100644 index 0000000000..16c1308d73 --- /dev/null +++ b/api/src/main/java/run/halo/app/plugin/event/PluginStartedEvent.java @@ -0,0 +1,17 @@ +package run.halo.app.plugin.event; + +import org.springframework.context.ApplicationEvent; + +/** + * The event that is published when a plugin is really started, and is only for plugin internal use. + * + * @author johnniang + * @since 2.17.0 + */ +public class PluginStartedEvent extends ApplicationEvent { + + public PluginStartedEvent(Object source) { + super(source); + } + +} diff --git a/application/src/main/java/run/halo/app/plugin/HaloPluginManager.java b/application/src/main/java/run/halo/app/plugin/HaloPluginManager.java index 9e9ea9bf48..76b44f870e 100644 --- a/application/src/main/java/run/halo/app/plugin/HaloPluginManager.java +++ b/application/src/main/java/run/halo/app/plugin/HaloPluginManager.java @@ -20,11 +20,15 @@ import org.pf4j.PluginFactory; import org.pf4j.PluginLoader; import org.pf4j.PluginRepository; +import org.pf4j.PluginState; +import org.pf4j.PluginStateEvent; +import org.pf4j.PluginStateListener; import org.pf4j.PluginStatusProvider; import org.pf4j.PluginWrapper; import org.springframework.context.ApplicationContext; import org.springframework.data.util.Lazy; import run.halo.app.infra.SystemVersionSupplier; +import run.halo.app.plugin.event.PluginStartedEvent; /** * PluginManager to hold the main ApplicationContext. @@ -56,6 +60,9 @@ public HaloPluginManager(ApplicationContext rootContext, setSystemVersion(systemVersionSupplier.get().getNormalVersion()); super.initialize(); + + // the listener must be after the super#initialize + addPluginStateListener(new PluginStartedListener()); } @Override @@ -175,4 +182,30 @@ public List getDependents(String pluginId) { } return dependents; } + + /** + * Listener for plugin started event. + * + * @author johnniang + * @since 2.17.0 + */ + private static class PluginStartedListener implements PluginStateListener { + + @Override + public void pluginStateChanged(PluginStateEvent event) { + if (PluginState.STARTED.equals(event.getPluginState())) { + var plugin = event.getPlugin().getPlugin(); + if (plugin instanceof SpringPlugin springPlugin) { + try { + springPlugin.getApplicationContext() + .publishEvent(new PluginStartedEvent(this)); + } catch (Throwable t) { + var pluginId = event.getPlugin().getPluginId(); + log.warn("Error while publishing plugin started event for plugin {}", + pluginId, t); + } + } + } + } + } } diff --git a/application/src/main/java/run/halo/app/plugin/event/HaloPluginStateChangedEvent.java b/application/src/main/java/run/halo/app/plugin/event/HaloPluginStateChangedEvent.java deleted file mode 100644 index 433268da87..0000000000 --- a/application/src/main/java/run/halo/app/plugin/event/HaloPluginStateChangedEvent.java +++ /dev/null @@ -1,36 +0,0 @@ -package run.halo.app.plugin.event; - -import org.pf4j.PluginState; -import org.pf4j.PluginWrapper; -import org.springframework.context.ApplicationEvent; - -/** - * Plugin state changed event. - * - * @author guqing - * @date 2021-11-06 - */ -public class HaloPluginStateChangedEvent extends ApplicationEvent { - - private final PluginWrapper plugin; - - private final PluginState oldState; - - public HaloPluginStateChangedEvent(Object source, PluginWrapper wrapper, PluginState oldState) { - super(source); - this.plugin = wrapper; - this.oldState = oldState; - } - - public PluginWrapper getPlugin() { - return plugin; - } - - public PluginState getOldState() { - return oldState; - } - - public PluginState getState() { - return this.plugin.getPluginState(); - } -}