2

I'm trying to create a proxy for a given Runnable object using the following code:

public class WorkInvocationHandler implements InvocationHandler {

    public static Runnable newProxyInstance(Runnable work) 
    {
        return (Runnable)java.lang.reflect.Proxy.newProxyInstance(
            work.getClass().getClassLoader(),
            getInterfacesWithMarker(work),
            new WorkInvocationHandler(work));
    }

    private static Class[] getInterfacesWithMarker(Runnable work)
    {
        List allInterfaces = new ArrayList();

        // add direct interfaces
        allInterfaces.addAll(Arrays.asList(work.getClass().getInterfaces()));

        // add interfaces of super classes
        Class superClass = work.getClass().getSuperclass();
        while (!superClass.equals(Object.class))
        {
          allInterfaces.addAll(Arrays.asList(superClass.getInterfaces()));
          superClass = superClass.getClass().getSuperclass();
        }

        // add marker interface
        allInterfaces.add(IWorkProxy.class);

        return (Class [])allInterfaces.toArray(new Class[allInterfaces.size()]);        
    }
}

The proxy should implement all interfaces that the given object implements with the additional marker interface that indicates whether the proxy was already created. Since I don't know for sure that the given object implements Runnable directly I traverse also on all super classes, however I assume that if it implements another interface that implements Runnable it will work so I don't need to traverse also on interfaces hierarchy.

However, I still get ClassCastException when trying to cast the proxy to Runnable:

java.lang.ClassCastException: $Proxy24 incompatible with java.lang.Runnable

I'm trying to think what could cause this exception. The class hierarchy of the given object is not available.

Any ideas ?

1
  • Try passing desired interfaces directly into invocation of newProxyInstance() (i.e. Array constructed in place) and see if it works. Commented Apr 11, 2011 at 13:50

2 Answers 2

2

UPDATE removed useless code.

This is not the problem, but you should use a Set<Class<?>> when you gather all the interfaces because you can get duplicates of the same interface in the hierarchy.

Sign up to request clarification or add additional context in comments.

1 Comment

Correct. In additional tests I did I got java.lang.IllegalArgumentException: repeated interface: java.lang.Runnable. Using Set solved this problem
1

Your code to walk the super classes is wrong. Replace

superClass = superClass.getClass().getSuperclass();

with

superClass = superClass.getSuperclass();

Otherwise you'll quickly take a detour to java.lang.Class and then to java.lang.Object.

1 Comment

Makes sense. so it's actually much simpler than I thought :). Thx

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.