Velth
Velth

Reputation: 1108

Java Weld CDI alternative Factory

In my production code I have an factory, this factory should be mocked in my test code. I have an interface which both factories implement:

public interface FtpTransferFactory {

    FtpTransfer createFtpTransfer(String host, String machine);

}

Production code:

@Default
public class FtpTransferFactoryImpl implements FtpTransferFactory {

    public FtpTransferFactoryImpl() {
    }

    @Override
    public FtpTransfer createFtpTransfer(final String host, final String machine) {
    return new FtpTransfer(); // Some real ftp transfer object
    }

}

Test code:

@Alternative
public class FtpTransferFactoryTestImpl implements FtpTransferFactory {

    @Override
    public FtpTransfer createFtpTransfer(String host, String machine) {
    return ...; // Some real ftp transfer object, with different settings (test env)
    }

}

In the beans.xml located at src/test/resources:

<alternatives>
    <class>engine.FtpTransferFactoryTestImpl</class>
</alternatives>

My implementing class:

@Default
public class SomeClass
    /** Ftp Factory */
    @Default
    @Inject
    private FtpTransferFactory ftpFactory;

    ...
}

When I execute my unit tests my implementing class still ends up with the production factory instead of the test factory. However, when I put the -element into my src/main/resources (production) it does work. But I don't want that since i'm putting testing code into production code. I've seen several tutorials doing it via this method... what I'm a doing wrong?

Upvotes: 0

Views: 1179

Answers (1)

Harald Wellmann
Harald Wellmann

Reputation: 12865

The classes in src/main/resources and src/test/resources are two separate bean deployment archives (BDA). A beans.xml descriptor only affects the current BDA.

So your <alternative> definition only affects your test classes but not your production classes.

If you use CDI 1.1, you can make your alternative global (i.e. activate it for all BDAs in your application) by adding a @Priority annotation.

On CDI 1.0, you could try using @Specializes instead of @Alternative to override your default bean.

Upvotes: 1

Related Questions