Hi Guillaume, I don’t completely understand what you mean by local/global…. and my knowledge of CDI is much less than either your or Ray’s knowledge.
Lets consider a request-scoped CDI bean A into which we’ve injected a service from a DS component B which has a mandatory reference to service C. If we start to unregister C, B’s deactivate method will be called. If A was a DS component, with a mandatory reference to B, first A’s deactivate method would be called. But iA is a CDI bean. Should deactivate on B be postponed until A goes out of scope (the request completes)? This would be somewhat similar to, if A was DS component, having a read-write lock where all the service methods get a read lock and the DS lifecycle methods get the write lock. Is this related to what you mean by local/global? hoping for more concrete details… thanks david jencks > On Nov 23, 2016, at 12:10 PM, Guillaume Nodet <[email protected]> wrote: > > > 2016-11-23 19:48 GMT+01:00 Raymond Auge <[email protected] > <mailto:[email protected]>>: > So let's purely focus on scopes then. Because as far as I've observed, in my > limited CDI experience, is that there are really only two scopes in CDI, > technically: > > - singleton > - not-singleton or rather "limited by some boundary" > > I'd say those are the same. The singleton scope is just one scope which uses > boundaries equals to the container lifecycle. > > > Take any CDI scope and you can fit it in one of those two buckets: > > ApplicationScoped > ConversationScoped > RequestScoped > SessionScoped > Dependent > Singleton > etc. > > Enter any custom scope and they should pretty much fall into one of those two > buckets. > > Yes, they all define a boundary. > > > The instance either lives from the beginning of the application 'til the end > OR some "Context" logic instantiates an instance at some point in time, and > later releases it. Perhaps multiple threads create their own instance, > perhaps the instance lives during the life of a transaction, etc. The > business logic around the actual lifetime is irrelevant, but the > instantiation and reclamation is important. > > The one difference in scopes that exists in OSGi but not in CDI is "osgi > bundle scope" vs "osgi singleton scope". However this difference only relates > to what CDI can emit or consume from OSGi as services. Internally it would > have no meaning because the CDI container is fundamentally scoped to the > bundle (at least in terms of the RFC requirements... which I think are sound > in this case) and so it need not concern itself to distinguish between a > singleton scoped service and a bundle scoped service (but it can certainly > force the requirement either way if it really wishes but internally to CDI it > makes no difference). > > In fact, the bean wrapper we place around OSGi services is really the > guardian of how the implementation creates and destroys instances based on > the context of the CDI scope. > > However, the OSGi service layer very nicely abstracts this for us in a clever > way for which we don't necessarily need to concern ourselves over the > context, and lifetime (or boundary) of the scope. > > If we simply always assume and use of the OSGi prototype API, then we > transparently satisfy any boundaries implemented by the CDI scope because the > osgi prototype API transparently supports services which are any of > singleton, bundle or prototype scope. > > So with a single bean implementation around all osgi services we safely > support pretty much any CDI scope. > > What do you mean by "supporting any CDI scope" ? You mean exposing beans > with any CDI scope in the OSGi registry ? > I'm not sure I understand what that would mean exporting a @RequestScoped > bean as an OSGi service. > > > The problem then becomes having a mechanism to enforce that a given scope > really only allows binding prototype scoped osgi services, but I think this > is not a real issue. It sounds reasonable that people would not redefine a > singleton, or application scope, and in that respect we could simply assume > that if the scope is not explicitly declared as: > > Singleton > ApplicationScoped > BundleScoped (osgi cdi spec) > SingletonScoped (osgi cdi spec?? not really sure we need to redefine this) > > that we automatically assume they should require prototype scoped services in > order to satisfy the fact that the scope needs to create and destroy > instances at it's own leisure. > > 😕😲🙄 Hopefully that made some kind of sense!!! > > I'm not sure that we have to think about exposing OSGi services the way you > do. I don't see the use case for choosing any CDI bean from an existing > application and exposing is over OSGi. Services are usually well defined > interfaces so there is a decision to expose a service in the OSGi registry. > So I'm fine with using custom annotations if needed. > Also, I'm not sure what you describe accomodates with the exposed bean > lifecycle having to be tied to its dependencies as I advocate. > > So basically I'm fine with the 3 scopes defined in the RFC when exposing > beans OSGi services: > * BundleScoped > * PrototypeScoped > * SingletonScoped > We could do some mapping with existing CDI scopes if needed. > But my main concern is certainly not that one. > > My concern is about the lifecycle when you inject services from the OSGi > registry into a CDI bean, not exporting services. > As I indicated in my first email, my concern is about handling OSGi > dynamics, not exporting OSGi services which is the easy part, and not about > CDI extensions, which I fully agree we need to support. > > What I'd like is a real injection framework that we can point OSGi users to. > Blueprint has some deficiencies ; the service damping mechanism is a pain to > deal with and also a pain to work around. > DS is very good at handling OSGi dynamics : it supports a great range of use > cases and the defaults makes users life easy. The problem with DS is that > it's limited to wiring OSGi services together, it's not pluggable, and can't > do anything else. > > If I'm understanding things right: > * if you inject an OSGI service into a bean, the while container lifecycle > will be tied to the availability of that bean > * if you use an optional dependency, a null proxy is injected > That's basically the only 2 scenarios supported by the RFC for injecting > services. > > My proposal supports: > * mandatory / optional > * greedy / reluctant > * static / dynamic > * local / global > Those should not deviate from the fact that a bean will never change during > it's lifecycle. The way to implement that is to make the bean lifecycle > boundary defined by the availability of its dependencies. It means beans > injected with OSGi services have to be in a custom CDI scope so that its > lifecycle can be managed. So whenever the dependencies of a CDI bean > injected with OSGi services change in a way that the bean needs to be > re-injected, we destroy the bean correctly and re-create it with the new > dependencies. IT supports the mandatory / optional and greedy / reluctant DS > semantics. > We also have the use case where you have a bean, but you don't want the > lifecycle to be modified and you want a proxy to be injected to use service > damping. It's not the default, but it can be supported. That's the static / > dynamic semantic. > There are some use cases where you don't want to change the scope. For those > use cases, the injection point needs to be flagged properly so that the whole > container lifecycle will be tied to the dependencies. That's the local / > global semantic which does not exist in DS. > > On the other side, i.e. exposing a service, there is: > * bundle / service / prototype service scope > * immediate / delayed > > A bunch of other things that should be supported: > * injecting configuration using annotations as in DS (configuration can be > mandatory / optional, greedy / reluctant) : an annotation defines the > injected config with optional default values, as specified in DS 112.8.2 > * injecting Instance<X> for mutiple cardinality injection > * filtering using generic filters or attributes (attributes can be used > also when exposing services and can hide > > So yes, I need a custom scope to support the above use cases. But that makes > things actually useful for OSGi developers imho, and not only simple use > cases for EE developers porting applications to OSGi. Supporting all well > known DS semantics ensures a complete usability for all known OSGi use cases. > I think if we go this way, we can end up with something really useful for > both OSGi beginners and more seasoned OSGi developers. > > Guillaume > > > - Ray > > > > On Wed, Nov 23, 2016 at 12:48 PM, Guillaume Nodet <[email protected] > <mailto:[email protected]>> wrote: > > > 2016-11-23 18:40 GMT+01:00 Raymond Auge <[email protected] > <mailto:[email protected]>>: > > > On Wed, Nov 23, 2016 at 12:34 PM, Guillaume Nodet <[email protected] > <mailto:[email protected]>> wrote: > > > 2016-11-23 18:22 GMT+01:00 Raymond Auge <[email protected] > <mailto:[email protected]>>: > Actually, we have a perfect solution in OSGi for the scenario of intermittent > scopes like web requests, session scope, etc. That is prototype scope! This > is already suggested by the requirements and works very well with the scoped > bean concept. You need a Provider for those beans and an OSGi prototype scope > service is the perfect provider including reclamation and destruction. > > Finally, we do want to support existing CDI extensions because that's where a > lot of the value is (JSF, JPA, JMS, etc.) and we don't want to change their > understanding of the lifecycle of CDI beans otherwise they will break and > people won't like it and lose faith that it's useful. > > My fear is to over-dynamic-fication of things which are not inherently > dynamic and fail to produce something useful. > > The point here is that people can still assemble modular apps using peer > bundles containing extensions, beans, osgi services in as complex or simple a > constellation as they need and everything needs very little change; that > adding and removing bundles from this constellation will behave as expected > in a dynamic environment. In fact existing things should largely work with > only slight metadata changes including; extensions and support for OSGi > services in existing code work without any code changes. > > Lastly, CDI is fundamentally the same as spring in that when the "container" > is declared to be done... it's done! It's like you've exited the constructor > of an object. It's effectively a static singleton and that behaviour is > expected by pretty much everything that uses it. Invariants introduced after > the fact such as trying to shoehorn dynamicity on individual beans I believe > will simply break peoples understanding and will cause OSGi's impl to diverge > too far away from future CDI work, which I feel is WAY too important to risk > since CDI is being introduced on other non-Java EE specifications and will > soon touch the JRE. > > Are you basically taking @RequestScoped and @SessionScoped out of the CDI > spec ? Or implying those scopes do not work well with JPA, JMS, JSF etc... ? > Or is there something I'm not understanding in CDI ? > > Hmm, I'm not sure how that got inferred by what I said. What I said was > literally: > > >Actually, we have a perfect solution in OSGi for the scenario of > >intermittent scopes like web requests, session scope, etc. That is prototype > >scope! This is already suggested by the requirements and works very well > >with the scoped bean concept. > > And you're ruling out the existence of other scopes or that the spec supports > custom scopes. The prototype scope is the default scope, it does not mean > it's the only one. @RequestScope and @SessionScope do handle dynamics very > well : the beans are not created until a request or session exist and is > destroyed when the request / session is destroyed : if that's not dynamic, > I'm not sure what it is. > That's what I'm proposing : having the ability to use a custom scope to > support more OSGi dynamics. > My solution has both a global lifecycle suited to porting JEE applications > (where the whole container lifecycle is tied to the global set of > dependencies) and one custom scope that can handle specific bean lifecycles, > so that OSGi users can benefit from a correct support of OSGi dynamism as in > DS. > > > Furthermore, JPA, JMS, JSF should be implementable as extensions as they > pretty much are in CDI already and why CDI can be used without any of those > features available. The use of those features in your applications however > infer the requirement on an extension capability providing them which should > be available so your application can function. > > I don't see how having extensions is related to scopes and lifecycle. > Supporting extensions is a must-have in CDI. What you implied is that > because you want to support extensions, we can't use custom scopes. I think > I was the one to suggest using generic capabilities to support extension in > the RFC years ago. > > And to answer your other email, I do not pretend to have a really good > knowledge of CDI (really, I don't). I may be missing things in using custom > scopes, but I'd like to understand what exactly, if any. > > > Does that make sense? > - Ray > > > > But this is just my opinion, > - Ray > > > On Wed, Nov 23, 2016 at 11:38 AM, Christian Schneider > <[email protected] <mailto:[email protected]>> wrote: > I think it would be great if Guillaume and Ray could work on the impl > together. Ray could then feed the experiences back into the RFC. > In any case I would support having Ray as an aries committer. > > Christian > > On 23.11.2016 17:30, David Bosschaert wrote: > Hi Guillaume, > > My understanding is that the technical design of the RFC will be > significantly changed to better support the OSGi dynamics - hopefully we'll > see an update soon at https://github.com/osgi/design/tree/master/rfcs/rfc0193 > <https://github.com/osgi/design/tree/master/rfcs/rfc0193> > > If I understand things correctly then Ray's CDI implementation will support > the improved design. > > Cheers, > > David > > -- > Christian Schneider > http://www.liquid-reality.de <http://www.liquid-reality.de/> > > Open Source Architect > http://www.talend.com <http://www.talend.com/> > > > > > -- > Raymond Augé <http://www.liferay.com/web/raymond.auge/profile> (@rotty3000) > Senior Software Architect Liferay, Inc. <http://www.liferay.com/> (@Liferay) > Board Member & EEG Co-Chair, OSGi Alliance <http://osgi.org/> (@OSGiAlliance) > > > > -- > ------------------------ > Guillaume Nodet > ------------------------ > Red Hat, Open Source Integration > > Email: [email protected] <mailto:[email protected]> > Web: http://fusesource.com <http://fusesource.com/> > Blog: http://gnodet.blogspot.com/ <http://gnodet.blogspot.com/> > > > > > -- > Raymond Augé <http://www.liferay.com/web/raymond.auge/profile> (@rotty3000) > Senior Software Architect Liferay, Inc. <http://www.liferay.com/> (@Liferay) > Board Member & EEG Co-Chair, OSGi Alliance <http://osgi.org/> (@OSGiAlliance) > > > > -- > ------------------------ > Guillaume Nodet > ------------------------ > Red Hat, Open Source Integration > > Email: [email protected] <mailto:[email protected]> > Web: http://fusesource.com <http://fusesource.com/> > Blog: http://gnodet.blogspot.com/ <http://gnodet.blogspot.com/> > > > > > -- > Raymond Augé <http://www.liferay.com/web/raymond.auge/profile> (@rotty3000) > Senior Software Architect Liferay, Inc. <http://www.liferay.com/> (@Liferay) > Board Member & EEG Co-Chair, OSGi Alliance <http://osgi.org/> (@OSGiAlliance) > > > > -- > ------------------------ > Guillaume Nodet > ------------------------ > Red Hat, Open Source Integration > > Email: [email protected] <mailto:[email protected]> > Web: http://fusesource.com <http://fusesource.com/> > Blog: http://gnodet.blogspot.com/ <http://gnodet.blogspot.com/>
