5 Replies Latest reply on Apr 28, 2013 11:26 AM by pref

    Enable alternatives from top level beans.xml

    swiderski.maciej

      Hi,

       

      Bit of a background, there is one bean archive that in bundled as jar - archive-1.jar, this bean archive has service (bean) that requires interaction with user repository and the archive provides already several implementations (db, ldap, etc) that are marked as alternatives. Then there is a web application that can be deployed in different environments and thus requiring different implementation for the user repository connector.

       

      So I am trying to enable alternatives defined in archive-1.jar using the top level beans.xml that is located in WEB-INF of the web application. Unfortunately on deployment (JBoss AS 7.1) it complains about missing dependency as none of the alternatives where selected in the archive-1.jar/beans.xml.

       

      Is there any way to enable alternatives (and decorators) from the web app level without them being defined in the archive beans.xml file or that the one from web app will take precedence?

       

      Thanks in advance

      Maciej

        • 1. Re: Enable alternatives from top level beans.xml
          mkouba

          Hi Maciej,

          you don't have to select an alternative in the bean archive the alternative bean class is defined in. How does the unsatisfied dependency error look like? Also where is the bean with unsatisfied injection point located?

          • 2. Re: Enable alternatives from top level beans.xml
            swiderski.maciej

            Martin, thanks for quick reply.

             

            the bean with unsatisfied dependency is in the same library (archive-1.jar) but it's packages in web application that declares the right alternative.

             

            and the exception looks like this:

             

            Exception 0 :
            org.jboss.weld.exceptions.DeploymentException: WELD-001408 Unsatisfied dependencies for type [UserGroupCallback] with qualifiers [@Default] at injection point [[field] @Inject private org.jbpm.services.task.commands.TaskContext.userGroupCallback]
                      at org.jboss.weld.bootstrap.Validator.validateInjectionPoint(Validator.java:311)
                      at org.jboss.weld.bootstrap.Validator.validateInjectionPoint(Validator.java:280)
                      at org.jboss.weld.bootstrap.Validator.validateBean(Validator.java:143)
                      at org.jboss.weld.bootstrap.Validator.validateRIBean(Validator.java:163)
                      at org.jboss.weld.bootstrap.Validator.validateBeans(Validator.java:382)
                      at org.jboss.weld.bootstrap.Validator.validateDeployment(Validator.java:367)
                      at org.jboss.weld.bootstrap.WeldBootstrap.validateBeans(WeldBootstrap.java:380)
                      at org.jboss.as.weld.WeldContainer.start(WeldContainer.java:83)
                      at org.jboss.as.weld.services.WeldService.start(WeldService.java:76)
                      at org.jboss.msc.service.ServiceControllerImpl$StartTask.startService(ServiceControllerImpl.java:1811)
                      at org.jboss.msc.service.ServiceControllerImpl$StartTask.run(ServiceControllerImpl.java:1746)
                      at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:895)
                      at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:918)
                      at java.lang.Thread.run(Thread.java:680)
            
            
                      at org.jboss.as.weld.services.WeldService.start(WeldService.java:83)
                      at org.jboss.msc.service.ServiceControllerImpl$StartTask.startService(ServiceControllerImpl.java:1811) [jboss-msc-1.0.2.GA.jar:1.0.2.GA]
                      at org.jboss.msc.service.ServiceControllerImpl$StartTask.run(ServiceControllerImpl.java:1746) [jboss-msc-1.0.2.GA.jar:1.0.2.GA]
                      at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:895) [classes.jar:1.6.0_43]
                      at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:918) [classes.jar:1.6.0_43]
                      at java.lang.Thread.run(Thread.java:680) [classes.jar:1.6.0_43]
            
            

             

            Thanks

            • 3. Re: Enable alternatives from top level beans.xml
              mkouba

              In CDI 1.0 alternatives are selected for a bean archive only. So it's not possible to select it globally for your application (e.g. in your WEB-INF/classes). Declaring selected alternatives globally for an application is a new feature introduced in CDI 1.1 ...

              • 4. Re: Enable alternatives from top level beans.xml
                swiderski.maciej

                any workaround for this that you could suggest? Or only thing is to either package with different set of alternatives (saparate bean archives per alternative) or repackage of the dependency while building the web application?

                 

                Thanks

                • 5. Re: Enable alternatives from top level beans.xml
                  pref

                  We use an ugly workaround for this task. For example you have three implementations of some bean DevelopmentBean, TestBean and ProductionBean. Annotate all of them with something like @Environmental(DEV/TEST/etc). Then create an extension in which you can veto the annotated type in ProcessAnnotatedType event if it's @Environmental annotation value is different from the currently selected one.

                   

                  @Environmental(DEV) public class DevelopmentBean {}
                  @Environmental(TEST) public class TestBean {}
                  
                  ...
                  <X> void filterEnvironmentalBeans(@Observers ProcessAnnotatedType<X> event) {
                      Environmental env = event.getAnnotatedType().getAnnotation(Environmental.class);
                      if (env != null && !isInCurrentEnvironment(env)) {
                          event.veto();
                      }
                  }