frjaeger220 / google-guice

Automatically exported from code.google.com/p/google-guice
Apache License 2.0
0 stars 0 forks source link

Attempt to call methodInvocation.getThis results in StackOverflowError #281

Open GoogleCodeExporter opened 9 years ago

GoogleCodeExporter commented 9 years ago
(Sample Application is attached)

I was attempting to create an AOP Interceptor in a prototype app that would
mimic a Lifecycle Process.  Unfortunately a call to
methodInvocation.getThis(); caused a StackOverflowException.  Here is the
interceptor.

public class LifecycleInterceptor implements MethodInterceptor {
    private Set<Object> cache;

    public LifecycleInterceptor() {
        this.cache = new HashSet<Object>();
    }

    public Object invoke(MethodInvocation methodInvocation) throws Throwable {
        Object parentObject = methodInvocation.getThis(); //<--Stack
Overflow Occurs here
        if (cache.contains(parentObject)) {
            return methodInvocation.proceed();
        }
        cache.add(parentObject);
        return methodInvocation.proceed();
    }

    protected Set<Object> getCache() {
        return cache;
    }
}

Here is a snippet of the stack trace.

Exception in thread "main" java.lang.RuntimeException:
java.lang.reflect.InvocationTargetException
    at
com.google.inject.ConstructorInjector.construct(ConstructorInjector.java:161)
    at com.google.inject.InjectorImpl$ImplicitBinding.get(InjectorImpl.java:1006)
    at
com.google.inject.BindingBuilderImpl$FactoryProxy.get(BindingBuilderImpl.java:29
9)
    at com.google.inject.InjectorImpl$9$1.call(InjectorImpl.java:708)
    at com.google.inject.InjectorImpl.callInContext(InjectorImpl.java:747)
    at com.google.inject.InjectorImpl$9.get(InjectorImpl.java:702)
    at com.google.inject.InjectorImpl.getInstance(InjectorImpl.java:728)
    at com.evolutionnext.Application.main(Application.java:18)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.jav
a:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:90)
Caused by: java.lang.reflect.InvocationTargetException
    at
com.evolutionnext.EnterQuestionFrame$$EnhancerByGuice$$70c97c37$$FastClassByGuic
e$$b9fbb725.newInstance(<generated>)
    at
com.google.inject.cglib.reflect.FastConstructor.newInstance(FastConstructor.java
:40)
    at com.google.inject.ProxyFactory$4.newInstance(ProxyFactory.java:176)
    at
com.google.inject.ConstructorInjector.construct(ConstructorInjector.java:142)
    ... 12 more
Caused by: java.lang.StackOverflowError
    at
com.google.inject.InterceptorStackCallback.intercept(InterceptorStackCallback.ja
va:45)
    at
com.evolutionnext.EnterQuestionFrame$$EnhancerByGuice$$70c97c37.toString(<genera
ted>)
    at java.lang.String.valueOf(String.java:2827)
    at java.io.PrintStream.println(PrintStream.java:771)
    at com.evolutionnext.LifecycleInterceptor.invoke(LifecycleInterceptor.java:24)
    at
com.google.inject.InterceptorStackCallback$InterceptedMethodInvocation.proceed(I
nterceptorStackCallback.java:66)
    at
com.google.inject.InterceptorStackCallback.intercept(InterceptorStackCallback.ja
va:45)
    at
com.evolutionnext.EnterQuestionFrame$$EnhancerByGuice$$70c97c37.toString(<genera
ted>)
    at java.lang.String.valueOf(String.java:2827)
    at java.io.PrintStream.println(PrintStream.java:771)
    at com.evolutionnext.LifecycleInterceptor.invoke(LifecycleInterceptor.java:24)
    at
com.google.inject.InterceptorStackCallback$InterceptedMethodInvocation.proceed(I
nterceptorStackCallback.java:66)

Original issue reported on code.google.com by dh.evolu...@gmail.com on 12 Dec 2008 at 8:47

Attachments:

GoogleCodeExporter commented 9 years ago
The problem is you're (indirectly) calling equals() or hashCode() on the 
intercepted object. And that's getting 
intercepted, and you're getting into problems.

You can fix this by adding the following to the TOP of your method interceptor. 
This will prevent equals() and 
hashCode() from being intercepted:
  if (methodInvocation.getMethod().getDeclaringClass() == Object.class) {
    return methodInvocation.proceed();
  }

Original comment by limpbizkit on 28 Dec 2008 at 2:02

GoogleCodeExporter commented 9 years ago
Thanks. Is this going to be left without a fix then?  It seems that any call to
.getThis() will inevitably be penalized with this exception. 

Original comment by dh.evolu...@gmail.com on 28 Dec 2008 at 2:46

GoogleCodeExporter commented 9 years ago
it's not getThis() that causes the problem. It's getThis() followed by 
hashCode(). There's not much we can 
do here...

Original comment by limpbizkit on 28 Dec 2008 at 4:30