I am new to cdi producer pattern and so far I have seen examples producing simple content already known at initialization point of a class. Now I have to produce an instance created at runtime and filled with some data which also happens at runtime. Here is my current approach but to me it aint that good... Is there a better approach so please help me out with some patterns and practices
public class myBean {
private DataHolder dataHolder;
@Produces
public DataHolder {
// dataHolder is null until I later init instance
return dataHolder;
}
}
At some point in my code I set the dataHolder to new istance and allow futher injections to use runtime data by doing this:
dataHolder = new DataHolder(data1, data2, data3);
That looks kinda cheep :) is there a better way? or a nice pattern for producing cdi stuff?
Your approach is indeed clumsy because if there is an injection of DataHolder
any time before you initialize it - it will return null
(if you produce a @Dependent
object) or even crash (with any other scope).
I suggest you do some reading on Producer methods either in CDI spec or Weld doc.
Now, my take on this. The cleanest approach would be to let the body of the producer work do all the creation job every time. That means either:
DataHolder
in your MyBean
class ever since it's creation and read them (they have to be available to producer at all times)If you stick with returning a @Dependent
bean, your producer is allowed to return null
- you can make use of that if you so wish. The injection point can then expect a possible null value which can be interpreted as 'not yet initialized'. Or, if you need different scope (@ApplicationScoped
, @RequestScoped
, ...) then it's probably easier to create a second dummy implementation of DataHolder
which will, again, mean 'not yet implemented'.
Side note: Any manually created object (e.g. using new
) in CDI will not have it's injection points resolved automatically. That means, if you inject anything into DataHolder
while creating the DataHolder
itself using new
, there will be null
.