【问题标题】:How to unit test CDI with weld-se?如何使用weld-se对CDI进行单元测试?
【发布时间】:2013-09-29 17:02:39
【问题描述】:

我想使用weld-se 对CDI 进行单元测试。但是,我遇到了 Weld 无法解决 bean 的问题。我创建了一个小项目来演示 gradle 的构建问题。

我在<project-root> 文件夹中有以下文件:

./build.gradle
./src/main/java/cdi/Book.java
./src/main/resources/META-INF/beans.xml
./src/test/java/cdi/BookTest.java
./src/test/resources/META-INF/beans.xml

下面列出了每个文件的内容。

build.gradle

apply plugin: 'java'    
repositories {
    mavenCentral()
}    
dependencies {
    compile 'org.jboss.weld.se:weld-se:2.0.4.Final'
    testCompile 'junit:junit:4.11'
}

Book.java

package cdi;    
public class Book {
    private String title;    
    public String getTitle() {
        return title;
    }    
    public void setTitle(String title) {
        this.title = title;
    }
}

BookTest.java

package cdi;
import org.jboss.weld.environment.se.Weld;
import org.jboss.weld.environment.se.WeldContainer;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
public class BookTest {
    private static Weld weld;
    private static WeldContainer weldContainer;

    @BeforeClass
    public static void setupClass() {
        weld = new Weld();
        weldContainer = weld.initialize();
    }

    @AfterClass
    public static void teardownClass() {
        weld.shutdown();
    }

    @Test
    public void dummyTest() {
        Book book = weldContainer.instance().select(Book.class).get();
        book.setTitle( "foobar");
        assertEquals("foobar", book.getTitle());
    }
}

beans.xml(main/和test/下的两个beans.xml是一样的。)

<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee 
                           http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd"
       version="1.1" bean-discovery-mode="all">
</beans>

当我使用gradle clean build 构建项目时,我收到一个错误,如下所示。我用谷歌搜索,但无法使其工作。

非常感谢您的帮助。

org.jboss.weld.exceptions.UnsatisfiedResolutionException: WELD-001308 Unable to resolve any beans for Types: [class cdi.Book]; Bindings: [QualifierInstance{annotationClass=interface javax.enterprise.inject.Any, values={}, hashCode=868729182}]
    at org.jboss.weld.manager.BeanManagerImpl.getBean(BeanManagerImpl.java:824)
    at org.jboss.weld.bean.builtin.InstanceImpl.get(InstanceImpl.java:78)
    at cdi.BookTest.dummyTest(BookTest.java:29)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:271)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:70)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:27)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecuter.runTestClass(JUnitTestClassExecuter.java:80)
    at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecuter.execute(JUnitTestClassExecuter.java:47)
    at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassProcessor.processTestClass(JUnitTestClassProcessor.java:69)
    at org.gradle.api.internal.tasks.testing.SuiteTestClassProcessor.processTestClass(SuiteTestClassProcessor.java:49)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at org.gradle.messaging.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:35)
    at org.gradle.messaging.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
    at org.gradle.messaging.dispatch.ContextClassLoaderDispatch.dispatch(ContextClassLoaderDispatch.java:32)
    at org.gradle.messaging.dispatch.ProxyDispatchAdapter$DispatchingInvocationHandler.invoke(ProxyDispatchAdapter.java:93)
    at com.sun.proxy.$Proxy2.processTestClass(Unknown Source)
    at org.gradle.api.internal.tasks.testing.worker.TestWorker.processTestClass(TestWorker.java:103)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at org.gradle.messaging.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:35)
    at org.gradle.messaging.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
    at org.gradle.messaging.remote.internal.hub.MessageHub$Handler.run(MessageHub.java:355)
    at org.gradle.internal.concurrent.DefaultExecutorFactory$StoppableExecutorImpl$1.run(DefaultExecutorFactory.java:66)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
    at java.lang.Thread.run(Thread.java:724)

【问题讨论】:

  • Weld 针对 JAR 文件进行操作,用于扫描目的。您应该考虑使用 arquillian 来测试这种技术。
  • @John:谢谢。我已经在尝试 Arquillian。

标签: jakarta-ee cdi jboss-weld weld


【解决方案1】:

我遇到了完全相同类型的问题,这是由于将 META-INF/beans.xml 文件放入 build/resources/ 而不是 Gradle 的 build/classes 引起的。

据我所知,Weld 不会扫描没有 beans.xml 文件的类。

一个丑陋的解决方法是在运行测试之前更改 build.gradle 文件以复制文件。这对我有用,我目前不知道有任何不良副作用。

对 Gradle 文件的更改。

test.doFirst {
    copy {
        from 'build/resources/main/META-INF/beans.xml'
        into 'build/classes/main/META-INF/'
    }
    copy {
        from 'build/resources/test/META-INF/beans.xml'
        into 'build/classes/test/META-INF/'
    }
}

【讨论】:

  • 这对我有用。我应该提一下,没有必要在测试类中包含 beans.xml,因为它们(至少从 2.2.0 版开始)会自动启用 CDI。见github.com/BrynCooke/cdi-unit/issues/25
【解决方案2】:

你应该试试“针”:http://needle.spree.de/overview

它会为您处理简单的模拟/DI 任务,并且不需要完整的堆栈容器。 在您的情况下,您可以使用

@Rule
public final NeedleRule needle = new NeedleRule();
@Inject
private Book book;
...

【讨论】:

    【解决方案3】:

    我还创建了 CDI-Unit http://jglue.org/cdi-unit/

    源码树中有一个示例 gradle 项目: https://github.com/BrynCooke/cdi-unit/tree/master/cdi-unit-tests-gradle

    【讨论】:

      猜你喜欢
      • 2016-02-14
      • 2013-11-02
      • 2021-05-24
      • 1970-01-01
      • 2013-05-21
      • 1970-01-01
      • 2012-01-08
      • 1970-01-01
      • 2019-11-02
      相关资源
      最近更新 更多