CDI (Weld SE) not injecting inner dependencies when using Producer method

我的未来我决定 提交于 2019-12-25 08:30:14

问题


I'm using WELD SE on a standalone java project which seemed to work fine till I started using producers.

The producer method works - the container uses it, but never injects the inner pdependencies of the produced bean. When I remove the producer, it works normally. I can't find the cause even after a long search on the spec and on Google.

Example of a Producer:

@ApplicationScoped
public class LaminaValidadorProducer {

    private static final String XSD_PATH = getConfig("processador.xsd.path");
    private static final Map<VersaoLamina,String> XSD_PER_VERSION = new HashMap<>();
    static {
        XSD_PER_VERSION.put(VersaoLamina.V1, getConfig("processador.lamina.xsd.file"));
        XSD_PER_VERSION.put(VersaoLamina.V2, getConfig("processador.laminav2.xsd.file"));        
    }

    @Produces
    public LaminaValidador buildValidador() {
        return new LaminaValidador(XSD_PATH, XSD_PER_VERSION);
    }
}

LaminaValidador is injected normally, but its INNER attributes (marked with @Inject) are not being injected. THe project has a beans.xml with bean-discovery-mode="all".

Any clues on what's happening?


回答1:


This is not only a matter of SE and it is in fact a desired/expected behaviour of CDI.

The reason behind this is that normally, if you do not have producers, CDI creates the bean classes for you (by calling no-args constructor, or one with injections) and subsequently resolves the injection points within the bean (and does some other things, see spec). E.g. you leave the lifecycle management to CDI container.

On the other hand, using a producer is usually a way to create a bean out of a class where:

  • you cannot control lifecycle youself, e.g. EntityManager
  • you intergrate with other frameworks and they have complex initialization
  • you need to do some checks for external config before calling certain constructor
  • or you maybe want a bean for a primitive type (int)
  • and many many more use cases

Now this means you are responsible for the creation of the bean. And that includes any fields within. Container just takes the producer as a way to create a full-blown bean and assumes you took care or what the initialization required.

Now, from your question I judge you need the injection point resolution inside. There is no easy way, if any, to "enforce" the resolution manually due to static nature of CDI (and other, more complex reasons). Hence I would propose to use a different approach and leverage constructor injection or maybe initializer methods? If you provide more information, I might be able to help.



来源:https://stackoverflow.com/questions/40225429/cdi-weld-se-not-injecting-inner-dependencies-when-using-producer-method

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!