Java 使用src/test/META-INF/beans.xml中的替代生产者进行焊接

Java 使用src/test/META-INF/beans.xml中的替代生产者进行焊接,java,cdi,jboss-weld,weld,weld-se,Java,Cdi,Jboss Weld,Weld,Weld Se,我试图使用Weld SE 2.3.0.Final在测试期间交换注入依赖项的替代实现,方法是在src/test/resources/META-INF中提供不同的beans.xml <beans xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xm

我试图使用Weld SE 2.3.0.Final在测试期间交换注入依赖项的替代实现,方法是在
src/test/resources/META-INF
中提供不同的
beans.xml

<beans xmlns="http://java.sun.com/xml/ns/javaee" 
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
      http://www.oracle.com/webfolder/technetwork/jsc/xml/ns/javaee/beans_1_0.xsd">
</beans>
<beans xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
      http://www.oracle.com/webfolder/technetwork/jsc/xml/ns/javaee/beans_1_0.xsd">
    <alternatives>
        <class>com.test.testing.TestEngineProducer</class>
    </alternatives>
</beans>
它似乎总是使用
beans.xml的主版本,但我不知道为什么

首先,这里是支持课程

Engine.java

public interface Engine
{
    void start();
    void stop();
}
@Vetoed
public class DefaultEngine implements Engine
{

    public void start()
    {
        System.out.println("Cough cough vrummmmm");
    }

    public void stop()
    {
        System.out.println("Phhhut clank");
    }

}
@Vetoed
public class SportsEngine implements Engine
{

    public void start()
    {
        System.out.println("Vrummm vrummm vrummmm!");
    }

    public void stop()
    {
        System.out.println("Prrrrrr clunk");
    }

}
DefaultEngine.java

public interface Engine
{
    void start();
    void stop();
}
@Vetoed
public class DefaultEngine implements Engine
{

    public void start()
    {
        System.out.println("Cough cough vrummmmm");
    }

    public void stop()
    {
        System.out.println("Phhhut clank");
    }

}
@Vetoed
public class SportsEngine implements Engine
{

    public void start()
    {
        System.out.println("Vrummm vrummm vrummmm!");
    }

    public void stop()
    {
        System.out.println("Prrrrrr clunk");
    }

}
java

public class Car
{
    @Inject
    private Engine engine;

    public void startCar()
    {
        engine.start();
    }

    public void stopCar()
    {
        engine.stop();
    }

}
EngineProducer.java

public class EngineProducer
{

    @Produces
    public Engine getEngine()
    {
        return new DefaultEngine();
    }

}
@Alternative
public class TestEngineProducer
{

    @Produces
    public Engine getEngine()
    {
        return new SportsEngine();
    }

}
App.java

public class App 
{
    @Inject
    private Car car;

    public void main(@Observes ContainerInitialized event)
    {
        car.startCar();
        car.stopCar();
    }
}
以及
src/main/resources/META-INF

<beans xmlns="http://java.sun.com/xml/ns/javaee" 
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
      http://www.oracle.com/webfolder/technetwork/jsc/xml/ns/javaee/beans_1_0.xsd">
</beans>
<beans xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
      http://www.oracle.com/webfolder/technetwork/jsc/xml/ns/javaee/beans_1_0.xsd">
    <alternatives>
        <class>com.test.testing.TestEngineProducer</class>
    </alternatives>
</beans>
现在从测试代码开始,我想使用
sportengine
实现。所以我有以下几点

SportsEngine.java

public interface Engine
{
    void start();
    void stop();
}
@Vetoed
public class DefaultEngine implements Engine
{

    public void start()
    {
        System.out.println("Cough cough vrummmmm");
    }

    public void stop()
    {
        System.out.println("Phhhut clank");
    }

}
@Vetoed
public class SportsEngine implements Engine
{

    public void start()
    {
        System.out.println("Vrummm vrummm vrummmm!");
    }

    public void stop()
    {
        System.out.println("Prrrrrr clunk");
    }

}
testingineproducer.java

public class EngineProducer
{

    @Produces
    public Engine getEngine()
    {
        return new DefaultEngine();
    }

}
@Alternative
public class TestEngineProducer
{

    @Produces
    public Engine getEngine()
    {
        return new SportsEngine();
    }

}
AppTest.java

@RunWith(WeldJUnit4Runner.class)
public class AppTest
{

    @Inject
    private Car car;

    @Test
    public void testCar()
    {
        car.startCar();
        car.stopCar();
    }

}
WeldJUnit4Runner.java

public class WeldJUnit4Runner extends BlockJUnit4ClassRunner
{

    /** The test class to run. */
    private final Class<?> mKlass;
    /** Weld infrastructure. */
    private final Weld weld;
    /** The container itself. */
    private final WeldContainer container;

    /**
     * Runs the class passed as a parameter within the container.
     * 
     * @param klass
     *            to run
     * @throws InitializationError
     *             if anything goes wrong.
     */
    public WeldJUnit4Runner(final Class<Object> klass) throws InitializationError
    {
        super(klass);
        this.mKlass = klass;
        this.weld = new Weld();
        this.container = weld.initialize();
    }

    @Override
    protected Object createTest() throws Exception
    {
        final Object test = container.instance().select(mKlass).get();
        return test;
    }
}
当测试方法运行时,它应该打印出来

Vrummm vrummm vrummmm!
Prrrrrr clunk
但是,它似乎使用了
EngineProducer
而不是
testingineproducer
,并将输出打印两次

Cough cough vrummmmm
Phhhut clank
Cough cough vrummmmm
Phhhut clank
为什么不使用testbeans.xml


如果我把test beans.xml中的
部分放在main beans.xml中,那么它就可以工作了,但是我不想在测试时交换main/resources/META-INF中的beans.xml,这似乎是一个错误。它只使用src/main/resources/META-INF下的beans.xml版本

解决方案使用CDI-SE src/main/resources/META-INF/beans.xml下的beans.xml进行测试,您可能还需要将添加到beans.xml中

当您将代码导出到部署包(jar、war、ear)中时,您可以拥有另一个production beans.xml文件。不要忘记用生产bean.xml替换测试bean.xml

如果您正在开发web应用程序。您可以在WEB-INF下创建生产beans.xml。存在beans.xml的2版本,但WAS仅使用WEB-INF/beans.xml

<?xml version="1.0" encoding="UTF-8"?>
<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">
    <scan>
        <exclude name="org.jboss.weld.**" />
        <exclude name="com.your_package.EngineProducer" />
    </scan>
    <alternatives>
        <class>com.test.testing.TestEngineProducer</class>
    </alternatives>
</beans>

com.test.testing.testingineproducer

试试看,然后告诉我结果!我有同样的结果:(请将test/resources/META-INF/beans.xml移到src/main/resources/META-INF/beans.xml——应该可以正常工作是的,我确实尝试将
部分放在beans.xml的主版本中,这确实注入了
运动引擎
,但我想使用beans.xml的测试版本,原因是Weld Se只在运行jUnit测试时使用src/main/resources