我正在尝试在战争文件之外加载豆子。目标是应该可以在没有新的战争文件的情况下更改 jar 文件。
我的war文件包含外部jar作为提供的依赖项:
<dependency>
<groupId>com.lube</groupId>
<artifactId>foo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<scope>provided</scope>
</dependency>
我将jar文件添加到域目录(domain/lib/applibs)中的applibs文件夹中,并在部署过程中填写了library字段。
似乎没有从这个jar文件加载豆子(无法注入),但是可以使用该类(该类在当前类加载器中可用)。
如果我在war文件的某个类中注入内容,我会得到以下异常< code > UnsatisfiedResolutionException:WELD-001334:带有限定符的XXX类型的不满足的依赖项
我使用payara4.1.2.174,但它不工作与payara 5太。
主要问题是:是否有可能在战争之外加载bean(ejb/cdi)?我在网上找不到任何好的解决方案。
备注:我不能使用微服务;)
编辑:war文件不包含jar文件。jar文件当前位于/lib/appliebs下的域中(我也测试了所有其他文件夹)
我如何做到这一点的命令是以下asadmin add-library--type app C:\library.jar
该库.jar仅包含一个 CDI Bean
@Model
public class CdiBean {
public void test() {
System.out.println("It works!");
}
}
和豆子.xml文件。(资源/META-INF - 我在没有 META-INF 文件夹的情况下也对其进行了测试)
WAR 文件有一个尝试加载 Bean 的启动类。
@Singleton
@Startup
@TransactionManagement(value = javax.ejb.TransactionManagementType.BEAN)
public class AppStartup {
@PostConstruct
public void postConstruct() {
try {
System.out.println(CdiBean.class);
CDI.current().select(CdiBean.class).get().test();
} catch (Exception e) {
throw new IllegalStateException(e.getMessage(), e);
}
}
}
战争部署后的产出是:
[2020-01-21T13:47:36.413+0100] [Payara 4.1] [INFO] [] [] [tid: _ThreadID=103 _ThreadName=admin-thread-pool::admin-listener(3)] [timeMillis: 1579610856413] [levelValue: 800] [[ class com.lube.CdiBean]]
[2020-01-21T13:47:36.474+0100] [Payara 4.1] [SEVERE] [] [javax.enterprise.system.tools.deployment.common] [tid: _ThreadID=103 _ThreadName=admin-thread-pool::admin-listener(3)] [timeMillis: 1579610856474] [levelValue: 1000] [[
Exception while invoking class org.glassfish.ejb.startup.EjbApplication start method
javax.ejb.EJBException: javax.ejb.CreateException: Initialization failed for Singleton AppStartup
...
Caused by: javax.ejb.CreateException: Initialization failed for Singleton AppStartup
at com.sun.ejb.containers.AbstractSingletonContainer.createSingletonEJB(AbstractSingletonContainer.java:553)
at com.sun.ejb.containers.AbstractSingletonContainer.access$000(AbstractSingletonContainer.java:82)
at com.sun.ejb.containers.AbstractSingletonContainer$SingletonContextFactory.create(AbstractSingletonContainer.java:723)
... 72 more
Caused by: java.lang.IllegalStateException: WELD-001334: Unsatisfied dependencies for type CdiBean with qualifiers
... 74 more
Caused by: org.jboss.weld.exceptions.UnsatisfiedResolutionException: WELD-001334: Unsatisfied dependencies for type CdiBean with qualifiers
... 102 more
]]
经过3天的测试,我找到了一个解决方案-最终:D我没有找到任何解决方案,所以我在payara github repo中搜索“appliebs”,我发现了以下interesting类<代码>appserver/web/weld-integration/src/main/java.org/glassfish/weld/DeploymentImpl.java
有一个名为的方法称为私有void进程BdasForAppLibs(ReadableArchive存档,DeploymentContext上下文)
,带有漂亮的java文档。
// These are application libraries that reside outside of the ear. They are usually specified by entries
// in the manifest.
// to test this put a jar in domains/domain1/lib/applibs and in its manifest make sure it has something like:
// Extension-Name: com.acme.extlib
// In a war's manifest put in something like:
// Extension-List: MyExtLib
// MyExtLib-Extension-Name: com.acme.extlib
在我发现我向 jar 文件添加了以下插件后:
<plugin>
<artifactId>maven-jar-plugin</artifactId>
<version>3.2.0</version>
<configuration>
<archive>
<manifestEntries>
<Extension-Name>com.lube</Extension-Name>
</manifestEntries>
</archive>
</configuration>
</plugin>
以及战争文件的以下内容
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>3.2.3</version>
<configuration>
<archive>
<manifestEntries>
<Extension-List>ExternalLib</Extension-List>
<ExternalLib-Extension-Name>com.lube</ExternalLib-Extension-Name>
</manifestEntries>
</archive>
</configuration>
</plugin>
之后,我构建了jar,并将其添加到域/lib/applibs
中。然后我部署了战争,一切都如预期!
添加库
命令。它可用于GlassFish Server,也可用于Payara Micro。我认为应该有这样的功能(不过我可以在Payara服务器上找到它)