ClassLoaderCache { public AggregateClassLoader getClassLoaderForProxy(Class<?> clazz, Set<Class<?>> interfaces) { TypesKey typesKey = new TypesKey(clazz, interfaces); AggregateClassLoader result = cache.get(typesKey); if (result == null) { result = newClassLoader(clazz, interfaces); AggregateClassLoader oldVal = cache.putIfAbsent(typesKey, result); if (oldVal != null) result = oldVal; } return result; }  AggregateClassLoader getClassLoaderForProxy(Class<?> clazz, Set<Class<?>> interfaces);  }
@Test public void testSameLoader() throws Exception { Class<BasicEntityImpl> clazz = BasicEntityImpl.class; ImmutableSet<Class<? extends Object>> interfaces = ImmutableSet.of(EntityProxy.class, Entity.class, EntityInternal.class, BasicEntity.class); AggregateClassLoader loader = cache.getClassLoaderForProxy(clazz, interfaces); assertLoader(loader, Iterables.concat(ImmutableList.of(clazz), interfaces)); AggregateClassLoader loader2 = cache.getClassLoaderForProxy(clazz, interfaces); assertSame(loader, loader2); }
@Test public void testDifferentLoader() throws Exception { Class<BasicEntityImpl> clazz = BasicEntityImpl.class; Set<Class<?>> interfaces = ImmutableSet.of(EntityProxy.class, Entity.class, EntityInternal.class, BasicEntity.class); AggregateClassLoader loader = cache.getClassLoaderForProxy(clazz, interfaces); assertLoader(loader, Iterables.concat(ImmutableList.of(clazz), interfaces)); Class<TestEntityImpl> clazz2 = TestEntityImpl.class; Set<Class<?>> interfaces2 = ImmutableSet.of(EntityProxy.class, Entity.class, EntityInternal.class, TestEntity.class); AggregateClassLoader loader2 = cache.getClassLoaderForProxy(clazz2, interfaces2); assertLoader(loader2, Iterables.concat(ImmutableList.of(clazz2), interfaces2)); assertNotSame(loader, loader2); }