[weld-dev] interceptors expected to be implemented via proxying or via subclassing?
Mark Struberg
struberg at yahoo.de
Mon May 17 12:36:13 EDT 2010
Thanks Marius!
That sums it up pretty well. My main concern is not _that_ we (OWB + Weld) currently work that way, but that this behaviour is not really explicitly stated.
I can well live with the behaviour because there are ways to work around it. But those ways should get clearly documented, otherwise we would confuse users pretty heavily.
For example:
public class MyService {
private @Inject MyService self;
@Secured(role=Admin)
public doA(){..}
@Secured(role=User)
public doU(){
self.doA();
}
}
txs and LieGrue,
strub
--- On Mon, 5/17/10, Marius Bogoevici <marius.bogoevici at gmail.com> wrote:
> From: Marius Bogoevici <marius.bogoevici at gmail.com>
> Subject: Re: [weld-dev] interceptors expected to be implemented via proxying or via subclassing?
> To: "Kenneth Saks" <ken.saks at oracle.com>
> Cc: "Pete Muir" <pmuir at redhat.com>, "Mark Struberg" <struberg at yahoo.de>, "Kenneth Saks" <Kenneth.Saks at sun.com>, "Weld-Dev List" <weld-dev at lists.jboss.org>
> Date: Monday, May 17, 2010, 4:18 PM
> Well ... I'm not considering
> interception of calls to 'this' an
> ideological issue, so I think the discussion is still open,
> but I want
> to add a few more elements to the discussion:
>
> Not only EJBs behave in this way (calls to "this" are not
> intercepted),
> but this is, for example, the case for Spring beans as well
> (notably,
> even when using subclassing via CGLib). The only case when
> Spring beans
> behave differently (and apply aspects on calls to "this")
> is when
> applying AspectJ load-time-weaving (which is a completely
> different kind
> of beast altogether).
>
> Of course that there is room for treating JSR-299 and EJBs
> differently
> wrt interception/decoration. The main question is whether
> we want to go
> that way or not. Now, there are plenty of cases when the
> invocation on
> an otherwise intercepted method will not be
> intercepted/decorated, like
> for example:
>
> public class SelfIntercepting {
>
> void method A() {
> }
>
> void method B() {
> }
>
> @AroundInvoke
> public void
> aroundInvoke(InvocationContext ctx) {
> ((SelfIntercepting)
> ctx.getTarget()).methodA();
> }
> }
>
> In this case a call to methodB does not go twice through
> methodA() - we
> know that getTarget() returns a non-intercepted instance
> (it's the
> spec). However, if we had this.methodA(), would be expect
> that to be
> intercepted?
>
> or, for example, if a decorator invokes a different method
> (B) on a
> delegate than the one it decorates (A), we do not apply the
> whole
> decorator chain on the new invocation, we just start at the
> next
> delegate. But, if the method (B) on the target class had an
> interceptor,
> will we expect it to be intercepted as well? Well ...
>
> I would be all for doing things as Mark says, as I
> recognize a lot of
> situations where that is useful and I understand some of
> the confusion,
> however, my considerations are that the price to be paid in
>
> inconsistency and need to clarify things on a case-per-case
> basis
> overweigh by far the benefits of a clear-cut explanation,
> albeit not
> satisfactory in all cases. I'd rather simply say: these are
> managed
> objects, therefore only contextual references are
> intercepted/decorated.
> There is a boundary that the container sets and we sort of
> have to live
> with that.
>
> Perhaps we could find a way to do something similar to what
> EJB does,
> i.e. ala
> @Inject @SelfDelegate SomeClasss contextualThis;
>
> I have to say it - this will not win an aesthetics contest,
> but I find
> it overall cleaner than dealing with the whole mess of
> "when is the
> method intercepted, when is it not".
>
>
> On 10-05-17 9:19 AM, Kenneth Saks wrote:
> > On May 17, 2010, at 5:45 AM, Pete Muir wrote:
> >
> >
> >> Hi Ken,
> >>
> >> Could you tell us where the EJB spec(s) says that
> you only don't have to intercept references to this?
> >>
> > Hi Pete,
> >
> > An EJB invocation is by definition an invocation on an
> EJB reference object. That's the only way to get the
> additional services (CMT, method authorization,
> special exception handling, interceptors, etc.) offered by
> the container. The caller never holds a direct
> reference to a bean instance.
> >
> > The case where code within a bean class method makes a
> direct Java invocation of another method in the bean class
> using "this" is just a plain Java SE method
> invocation. There's no container interposition
> involved. SessionContext.getBusinessObject()
> was defined in part to allow one business method to make a
> 1st class EJB invocation on its own bean.
> >
> > --ken
> >
> >
> >> Thanks!
> >>
> >> On 16 May 2010, at 09:36, Mark Struberg wrote:
> >>
> >>
> >>> Hoi!
> >>>
> >>> Sorry, only came back yesterday night, so I
> had no time to answere Marius' post before.
> >>>
> >>> Actually I don't really know if I should agree
> or not.
> >>>
> >>> I would not really argue with the EJB spec,
> because 299 and EJB are still different. For example in the
> EJB spec Interceptors doesn't need to be Serializable
> whereas in 299 they certainly do for passivatable scopes.
> >>>
> >>> Also, EJB-3.1 is coming from the EJB-2 mindset
> where you really have separated remotes and stubs and many
> people are _used_ that only remote calles get intercepted.
> But I actually didn't find that backed in the EJB-3.1 spec
> (4.3.12), any? Imo the spec does NOT say that interception
> only happens if business methods get invoked from external!
> It's only that _old_ EJB users got _used_ to that
> behaviour.
> >>>
> >>> Let's make a small example:
> >>>
> >>> public class MyService() {
> >>>
> >>> @Secured(role=Admin)
> >>> public void doThingA() {
> >>> }
> >>>
> >>> @Secured(role=User)
> >>> public void doThingU() {
> >>> ...
> >>> if (veryRareCase) {
> >>> doThingA()
> >>> }
> >>> }
> >>>
> >>> }
> >>>
> >>> Clearly we would allow to call doThingA
> without checking for admin rights. I don't like to split my
> classes depending on the interceptors I'd like to apply.
> That sounds _really_ dumb. Even more if you look at
> interceptors which get applied without annotating the
> classes in the code but from external like e.g. @Trace,
> @Statistics, etc.
> >>>
> >>> This also happens if you have services where
> not all methods share must be e.g. @Transactional or even
> worse, use @Transactional with different payload.
> >>>
> >>> WE know WHY this behaves that way, but for 99%
> of all users, this will get reported as bug (as seen on the
> OpenEJB list lot of times).
> >>>
> >>> I'm sure we can do better!
> >>>
> >>> LieGrue,
> >>> strub
> >>>
> >>>
> >>> --- On Wed, 5/12/10, Pete Muir<pmuir at redhat.com>
> wrote:
> >>>
> >>>
> >>>> From: Pete Muir<pmuir at redhat.com>
> >>>> Subject: Re: [weld-dev] interceptors
> expected to be implemented via proxying or via subclassing?
> >>>> To: "Marius Bogoevici"<marius.bogoevici at gmail.com>
> >>>> Cc: "Mark Struberg"<struberg at yahoo.de>,
> weld-dev at lists.jboss.org
> >>>> Date: Wednesday, May 12, 2010, 1:46 PM
> >>>> Agreed.
> >>>>
> >>>> On 11 May 2010, at 10:31, Marius Bogoevici
> wrote:
> >>>>
> >>>>
> >>>>> Mark,
> >>>>>
> >>>>> I asked a similar question
> here:
> >>>>> http://lists.jboss.org/pipermail/weld-dev/2010-April/002485.html
> >>>>>
> >>>>> Gurkan answered here:
> >>>>> http://lists.jboss.org/pipermail/weld-dev/2010-April/002490.html
> >>>>>
> >>>>> So based on what I think, and also on
> my understanding
> >>>>>
>
> >>>> of what Gurkan
> >>>>
> >>>>> says: one should not expect that
> invocations to 'this'
> >>>>>
>
> >>>> are
> >>>>
> >>>>> intercepted/decorated - that doesn't
> happen in EJB and
> >>>>>
>
> >>>> it is not
> >>>>
> >>>>> expected to happen for decorators.
> >>>>>
> >>>>> Marius
> >>>>>
> >>>>> On 10-05-11 2:24 AM, Mark Struberg
> wrote:
> >>>>>
>
> >>>>>> Hi!
> >>>>>>
> >>>>>> There is a subtle difference
> between implementing
> >>>>>>
>
> >>>> interceptors via proxy or via subclasses.
> >>>>
> >>>>>> I have the following service which
> imports data
> >>>>>>
>
> >>>> from a legacy system into my db. Since
> commits are very
> >>>> performance intense, they should get
> imported in packages of
> >>>> 100. So I'll get 100 'Employees' from my
> legacy system and
> >>>> then call a @Transactional method to store
> them in my own
> >>>> database.
> >>>>
> >>>>>> public void ImportService() {
> >>>>>> public void
> importEmployee() {
> >>>>>>
> >>>>>>
>
> >>>>
> List<LegacyEmployee> les;
> >>>>
> >>>>>> while ((les =
> >>>>>>
>
> >>>> getNext100EmployeesFromLegacy()) != nul)
> {
> >>>>
> >>>>>>
>
> >>>> importLegacyEmployees(le);
> >>>>
> >>>>>> }
> >>>>>> }
> >>>>>>
> >>>>>> @Transactional
> >>>>>> protected
> >>>>>>
>
> >>>>
> importLegacyEmployees(List<LegacyEmployee> les)
> >>>> {
> >>>>
> >>>>>> for
> (LegacyEmployee le:
> >>>>>>
>
> >>>> les) {
> >>>>
> >>>>>>
>
> >>>> employeeService.store(le);
> >>>>
> >>>>>> }
> >>>>>> }
> >>>>>> }
> >>>>>>
> >>>>>> This would actually _not_ work
> when using proxies
> >>>>>>
>
> >>>> for the interceptor handling, because
> calling a method on an
> >>>> own class doesn't invoke the
> proxyhandler.
> >>>>
> >>>>>> So is this expected to work?
> >>>>>>
> >>>>>> I remember that the old spec
> explicitly says that
> >>>>>>
>
> >>>> we need to use subclassing, but cannot
> find this paragraph
> >>>> anymore. So what does the spec require us
> to do? And what is
> >>>> Weld going to do?
> >>>>
> >>>>>> txs and LieGrue,
> >>>>>> strub
> >>>>>>
> >>>>>>
> >>>>>>
>
> >>>>>
>
> >>>>>>
> _______________________________________________
> >>>>>> weld-dev mailing list
> >>>>>> weld-dev at lists.jboss.org
> >>>>>> https://lists.jboss.org/mailman/listinfo/weld-dev
> >>>>>>
> >>>>>>
>
> >>>>>
> _______________________________________________
> >>>>> weld-dev mailing list
> >>>>> weld-dev at lists.jboss.org
> >>>>> https://lists.jboss.org/mailman/listinfo/weld-dev
> >>>>>
>
> >>>>
> >>>>
> >>>
> >>>
> >>>
> >>>
> _______________________________________________
> >>> weld-dev mailing list
> >>> weld-dev at lists.jboss.org
> >>> https://lists.jboss.org/mailman/listinfo/weld-dev
> >>>
> >>
> >
>
>
More information about the weld-dev
mailing list