sbp
sbp copied to clipboard
调用PluginMangaer.startPlugin(pluginId)方法时报错
作者您好有一个错误,不知道原因出在哪里。 调用PluginMangaer.startPlugin(pluginId)方法时报错,这个错误是偶发的,不是每次都报错。
是不是在IDE中运行才会报这个错? 可能是因为运行时, 插件没有被编译, application-dev.yml
没有被放入编译output目录中的原因.
参考这里: https://github.com/hank-cp/sbp/blob/master/docs/trouble_shoot.md#plugin-is-not-compiled-after-i-changed-code
不是的,是服务器上运行时报的错,而且是偶发的,但是只要一次失败,以后的就都失败了。这个是的配置文件和目录结构
请问你目前使用的sbp版本是多少? 部署方式是哪种? 打jar包部署, 还是直接部署class文件?
您好,我用的sbp版本是0.1.13,使用的springboot的版本是2.2.2Release。
这是我application的配置文件
是否是我的 classes-directories参数的值配置的有问题
如果是配置错误, 那就是必现问题而不应该是偶发问题.
如果方便的话, 请提供异常发生前后完整的log, 特别是cause异常. 需要知道为什么那个"application-dev.yml"为什么没能被加载.
调用PluginMangaer.startPlugin(pluginId)
之前还有其它动作吗? 如果是要更新插件的话, 调用reloadPlugin()
更好一些.
您好下面是我全量报错日志
sbp报错日志.txt
另外我使用的版本中PluginMangaer没有reloadPlugin()方法。
从以下这段log来看:
Caused by: java.lang.IndexOutOfBoundsException: null
at org.springframework.boot.loader.data.RandomAccessDataFile.getSubsection(RandomAccessDataFile.java:83) ~[platform-1.0.0-SNAPSHOT.jar:1.0.0-SNAPSHOT]
at org.springframework.boot.loader.jar.JarFileEntries.getEntryData(JarFileEntries.java:238) ~[platform-1.0.0-SNAPSHOT.jar:1.0.0-SNAPSHOT]
at org.springframework.boot.loader.jar.JarFileEntries.getInputStream(JarFileEntries.java:215) ~[platform-1.0.0-SNAPSHOT.jar:1.0.0-SNAPSHOT]
at org.springframework.boot.loader.jar.JarFile.getInputStream(JarFile.java:231) ~[platform-1.0.0-SNAPSHOT.jar:1.0.0-SNAPSHOT]
at org.springframework.boot.loader.jar.JarURLConnection.getInputStream(JarURLConnection.java:172) ~[platform-1.0.0-SNAPSHOT.jar:1.0.0-SNAPSHOT]
at java.net.URLClassLoader.getResourceAsStream(URLClassLoader.java:238) ~[na:1.8.0_181] // 这里有问题
启动Plugin的ApplicationContext时没有被使用正确的classloader, 应该通过SpringBootPluginClassLoader
去load资源文件才对. 要检查一下在plugin启动过程中有没有修改classloader或resourceLoader.
另外我使用的版本中PluginMangaer没有reloadPlugin()方法。
reloadPlugins()
是SpringBootPluginManager
的方法, 而你看截图的PluginManager
是它的父类. 你可以注入SpringBootPluginManager
去调用这个方法
这个我应该从哪里下手检查呢?debug启动方法没有发现不对的地方。
在application里加了一个pluginLoader,但是好像没什么影响
在单独的插件里面没有特殊的操作,用的就是super.start()方法
另外使用reloadPlugins方法也还是会报错,应该不是这个方法用错的问题
首先, 如果你的部署方式是直接读取class文件, 或者读取单个jar文件, 那么这个CustomPluginLoader可以删掉. 它是为了读取fat-jar那种特殊格式才需要用到的.
然后. 关于你的工程还有几个问题:
- 你线上环境采用的是哪种部署方式? 是直接部署classes文件还是打包成jar部署的? jar包是用示例工程的打包方式, 还是跟依赖库一起打包成fat-jar?
-
dev
是否是有意指定的profile? - 如果profile
dev
是有意指定的, 是通过哪种方式传递给插件的?
最后, 请在XXXPlugin.start()
方法中加入以下几行log, 观察加载的文件位置是否正确:
log.info("debug.0: " + this.wrapper.getPluginClassLoader());
log.info("debug.1: " + this.wrapper.getPluginClassLoader().getResource("application-dev.yml"));
try {
log.info("debug.2: " + new DefaultResourceLoader(getWrapper().getPluginClassLoader()).getResource("classpath:/application-dev.yml").getURL());
} catch (Exception ignored) {}
您好,按照您给的方式输出日志后,观察感觉报错时加载文件位置的路径没有问题。
关于我的工程的问题:
1、我的plugin的打包方式如下图
2、dev是有意指定的profile,通过启动命令在启动的时候指定的。
3、至于怎么传递给插件的这里的原理我也不太清楚,我没有特殊做过任何处理。貌似他会自动记录第一次启动时的profile
This issue was closed because it has been inactive.