use of org.apache.commons.collections.map.ReferenceMap in project jackrabbit by apache.
the class NodeTypeCache method getInstance.
/**
* @param service the repository service.
* @param userId the userId. If <code>null</code> this method will return a
* new cache instance for each such call.
* @return the <code>NodeTypeCache</code> instance for the given
* <code>service</code> and <code>userId</code>.
*/
public static NodeTypeCache getInstance(RepositoryService service, String userId) {
// if no userId is provided do not keep the cache
if (userId == null) {
return new NodeTypeCache();
}
Map<String, NodeTypeCache> caches;
synchronized (CACHES_PER_SERVICE) {
caches = CACHES_PER_SERVICE.get(service);
if (caches == null) {
// use soft references for the node type caches
caches = new ReferenceMap(ReferenceMap.HARD, ReferenceMap.SOFT);
CACHES_PER_SERVICE.put(service, caches);
}
}
synchronized (caches) {
NodeTypeCache cache = caches.get(userId);
if (cache == null) {
cache = new NodeTypeCache();
caches.put(userId, cache);
}
return cache;
}
}
use of org.apache.commons.collections.map.ReferenceMap in project gradle by gradle.
the class AbstractClassGenerator method generateUnderLock.
private <T> Class<? extends T> generateUnderLock(Class<T> type) {
Map<Class<?>, Class<?>> cache = GENERATED_CLASSES.get(getClass());
if (cache == null) {
// WeakHashMap won't work here. It keeps a strong reference to the mapping value, which is the generated class in this case
// However, the generated class has a strong reference to the source class (by extending it), so the keys will always be
// strongly reachable while this Class is strongly reachable. Use weak references for both key and value of the mapping instead.
cache = new ReferenceMap(AbstractReferenceMap.WEAK, AbstractReferenceMap.WEAK);
GENERATED_CLASSES.put(getClass(), cache);
}
Class<?> generatedClass = cache.get(type);
if (generatedClass != null) {
return generatedClass.asSubclass(type);
}
if (Modifier.isPrivate(type.getModifiers())) {
throw new GradleException(String.format("Cannot create a proxy class for private class '%s'.", type.getSimpleName()));
}
if (Modifier.isAbstract(type.getModifiers())) {
throw new GradleException(String.format("Cannot create a proxy class for abstract class '%s'.", type.getSimpleName()));
}
Class<? extends T> subclass;
try {
ClassMetaData classMetaData = inspectType(type);
ClassBuilder<T> builder = start(type, classMetaData);
builder.startClass(classMetaData.isShouldImplementWithServiceRegistry());
if (!DynamicObjectAware.class.isAssignableFrom(type)) {
if (ExtensionAware.class.isAssignableFrom(type)) {
throw new UnsupportedOperationException("A type that implements ExtensionAware must currently also implement DynamicObjectAware.");
}
builder.mixInDynamicAware();
}
if (!GroovyObject.class.isAssignableFrom(type)) {
builder.mixInGroovyObject();
}
builder.addDynamicMethods();
if (classMetaData.conventionAware && !IConventionAware.class.isAssignableFrom(type)) {
builder.mixInConventionAware();
}
Class noMappingClass = Object.class;
for (Class<?> c = type; c != null && noMappingClass == Object.class; c = c.getSuperclass()) {
if (c.getAnnotation(NoConventionMapping.class) != null) {
noMappingClass = c;
}
}
if (classMetaData.isShouldImplementWithServiceRegistry()) {
builder.generateServiceRegistrySupportMethods();
}
Set<PropertyMetaData> conventionProperties = new HashSet<PropertyMetaData>();
for (PropertyMetaData property : classMetaData.properties.values()) {
if (SKIP_PROPERTIES.contains(property.name)) {
continue;
}
if (property.injector) {
builder.addInjectorProperty(property);
for (Method getter : property.getters) {
builder.applyServiceInjectionToGetter(property, getter);
}
for (Method setter : property.setters) {
builder.applyServiceInjectionToSetter(property, setter);
}
continue;
}
boolean needsConventionMapping = false;
if (classMetaData.isExtensible()) {
for (Method getter : property.getters) {
if (!Modifier.isFinal(getter.getModifiers()) && !getter.getDeclaringClass().isAssignableFrom(noMappingClass)) {
needsConventionMapping = true;
break;
}
}
}
if (needsConventionMapping) {
conventionProperties.add(property);
builder.addConventionProperty(property);
for (Method getter : property.getters) {
builder.applyConventionMappingToGetter(property, getter);
}
}
if (needsConventionMapping) {
for (Method setter : property.setters) {
if (!Modifier.isFinal(setter.getModifiers())) {
builder.applyConventionMappingToSetter(property, setter);
}
}
}
}
Set<Method> actionMethods = classMetaData.missingOverloads;
for (Method method : actionMethods) {
builder.addActionMethod(method);
}
// Adds a set method for each mutable property
for (PropertyMetaData property : classMetaData.properties.values()) {
if (property.setters.isEmpty()) {
continue;
}
if (Iterable.class.isAssignableFrom(property.getType())) {
// Currently not supported
continue;
}
if (property.setMethods.isEmpty()) {
for (Method setter : property.setters) {
builder.addSetMethod(property, setter);
}
} else if (conventionProperties.contains(property)) {
for (Method setMethod : property.setMethods) {
builder.applyConventionMappingToSetMethod(property, setMethod);
}
}
}
for (Constructor<?> constructor : type.getConstructors()) {
if (Modifier.isPublic(constructor.getModifiers())) {
builder.addConstructor(constructor);
}
}
subclass = builder.generate();
} catch (Throwable e) {
throw new GradleException(String.format("Could not generate a proxy class for class %s.", type.getName()), e);
}
cache.put(type, subclass);
cache.put(subclass, subclass);
return subclass;
}
Aggregations