I have projectA
, projectB
, and projectC
Eclipse Maven projects.
ProjectA
contains:
IMyApi
interface.META-INF\beans.xml
file.ProjectB
contains:
IMyConfig
interface.MyConfigJndi
implementation of IMyConfig
.MyApiImpl
implementation of IMyApi
, with a property @Inject private IMyConfig config;
.META-INF\beans.xml
file.ProjectC
contains:
MyConfigAlter
implementation of IMyConfig
, marked as @Alternative
.Main
class (and method) that initializes Weld SE and retrieves a IMyApi
bean.META-INF\beans.xml
where MyConfigAlter
is listed in the alternatives
section.Now, I run the Main
class, and the IMyApi
bean is successfully retrieved (as a MyApiImpl
instance). But such an instance has been, in its config
property, injected with a MyConfigJndi
instance, instead of the alternative version (MyConfigAlter
)
I am using Eclipse Luna + M2Eclipse.
What am I doing wrong?
UPDATE: I found out that using @Specializes
instead of @Alternative
solves the issue, but I still think it is not the proper solution (in some situation I may not have access to the "default" implementation).
UPDATE 2:
I am using Weld-se, 2.2.10.Final:
<dependency>
<groupId>org.jboss.weld.se</groupId>
<artifactId>weld-se</artifactId>
<version>2.2.10.Final</version>
<scope>runtime</scope>
</dependency>
And the initialization is simply
WeldContainer weld =
new Weld().
initialize();
IMyApi myApi =
weld.
instance().
select(
IMyApi.
class).
get();
Selecting an alternative using the alternatives
element in the beans.xml
descriptor only affects the corresponding bean archive, i.e. ProjectC
in your case, as documented in Declaring selected alternatives for a bean archive. Based on that, this is logical that the ProjectB
bean archive gets the MyConfigJndi
implementation injected.
Since CDI 1.2, it is possible to select an alternative globally for the application using the @Priority
annotation as documented in Declaring selected alternatives for an application.
So in your case, you could write:
@Priority(Interceptor.Priority.Application)
@Alternative
class MyConfigAlter {
}