[cdi-dev] [JBoss JIRA] (CDI-139) Support for unmanaged instances

Pete Muir (Commented) (JIRA) jira-events at lists.jboss.org
Wed Nov 2 11:22:45 EDT 2011

    [ https://issues.jboss.org/browse/CDI-139?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=12639303#comment-12639303 ] 

Pete Muir commented on CDI-139:

> I think we don't need anything like that. It happens that all (non EG)
> people I talked about this very problem (using Instance<T> for creating
> @Dependent beans) did not even understand that they created a memory leak!
> What can we do against it? We could of course add a destroy(Object) instance,
> but this might be hard to use. Of course, users would really need to use it
> and old code would still be broken.

> My solution: the injected Instance<T> itself is a managed contextual instance 
> as well, and it has Scope @Dependent. Thus it is possible to add a @PreDestroy
> to it which will automatically get called by the container whenever the containing
> contextual instance will get destroyed.
> If we now in Instance#get() check if the created contextual instance is @Dependent
> and then store it in a List inside the respective Instance<T> instance, then we
> can also easily cleanup them in the @PreDestroy of Instance<T> which got used to 
> create all the Dependent contextual instances.

Yes, we should certainly clarify that this is the behavior required, and this is actually what creates the "memory leak" in the first place. The issue is most apparent you associate the Instance with an application scoped bean, it means the memory won't be released until the application is undeployed. This is correct, but has unfortunate side effects.

Weld implements this today, not via the impl you propose, but it has the same effect. There are a few optimisations we can do - if there is no @PreDestroy callback on the dependent bean, there is no need to hold a reference to it at all. We could also offer a mode where only a weak reference is held by Weld, so that when the app drops a reference, it can be gc'd.

We could of course suggest people don't use Instance with application scoped beans, but this seems a bad restriction.

I think offering a mode where people can manually clean up their Instances is useful. It won't affect the functionality of an app if you don't use it, but it can offer an optimisation people can use.

> Additionally we need to specify, when @Dependent instances that are obtained via CDI.current() or 
> BeanManager.getReference(...) are destroyed. At least this should be happen on container-shutdown.

Beans obtained via BeanManager must be manually cleaned up using Contextual.destroy().

We should add that instances obtained via CDI.current() will be treated as belonging to the lifecycle of the application, and so automatically cleaned up when the application is stopped. Can you file an issue for that?

IMO this latter point also emphasises the need for a Instance.destroy() method, most of the time people will want their beans cleaned before the application is stopped.
> Support for unmanaged instances
> -------------------------------
>                 Key: CDI-139
>                 URL: https://issues.jboss.org/browse/CDI-139
>             Project: CDI Specification Issues
>          Issue Type: Feature Request
>          Components: Beans
>    Affects Versions: 1.0
>            Reporter: Joshua Davis
>             Fix For: 1.1 (Proposed)
> Allow the creation of unmanaged instances.   The CDI context will not keep track of these instances and the application will be responsible for cleaning them up.   This is a fairly typical usage of other DI frameworks such as Guice and PicoContainer.
> Currently, if an ApplicationScoped object injects an {{Instance<T>}} interface, CDI will manage all instances returned by the {{get()}} method as dependents of the application scoped object.   Those instances will be kept in memory by the CDI implementation and will only be GC'd when the application scoped object is destroyed (at the end of the application).   This may look like a memory leak to the user (see WELD-920).
> From P. Muir on WELD-920
> {quote}
> We can describe instances which are attached (as the CDI 1.0 spec requires) as "managed" instances, and those which the user takes responsibility for cleaning up themselves as "unmanaged" instances. In CDI 1.1 I would like to add support for unmanaged instances (the impl will just hand these over and forget about them) and also to allow the app to request an unmanaged instance is cleaned up. Please can someone file a CDI issue for this?
> Weld could certainly be more friendly and more proactively discard instances. Ideas:
> 1) Analyse the dependent instance graph, and if there are no @PreDestroy/@Disposer callbacks on in the graph, do not store the dependent instance for cleanup (this would be a good general optimization
> (2) Add a config option to allow instances created from Instance to be held only as long as the app holds a reference, and if the app doesn't hold a reference for it's lifetime, then Weld would not do any cleanup (Weld would hold a weak ref).
> {quote}

This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators: https://issues.jboss.org/secure/ContactAdministrators!default.jspa
For more information on JIRA, see: http://www.atlassian.com/software/jira


More information about the cdi-dev mailing list