private void unregisterAsyncBean(final FactoryHandle handle) { final String name = (handle.getBeanName() != null ? handle.getBeanName() : handle.getActualType().getName()); typeNamesByName.remove(name, handle.getActualType().getName()); unloadedByFactoryName.remove(handle.getFactoryName()); for (final Class<?> assignable : handle.getAssignableTypes()) { final Iterator<UnloadedFactory<?>> unloadedIter = unloadedByTypeName.get(assignable.getName()).iterator(); while (unloadedIter.hasNext()) { final UnloadedFactory<?> unloaded = unloadedIter.next(); if (unloaded.getHandle().getFactoryName().equals(handle.getFactoryName())) { unloadedIter.remove(); break; } } } }
public static String beanDeftoString(final FactoryHandle handle) { return "[type=" + handle.getActualType().getName() + ", qualifiers=" + handle.getQualifiers() + "]"; }
@Override public Class<? extends Annotation> getScope() { return handle.getScope(); }
private void addFactory(final FactoryHandle handle) { for (final Class<?> assignableType : handle.getAssignableTypes()) { handlesByName.put(assignableType.getName(), handle); } if (handle.getBeanName() != null) { handlesByName.put(handle.getBeanName(), handle); } }
@SuppressWarnings({ "rawtypes", "unchecked" }) public Collection<SyncBeanDef> lookupBeans(final String name, final boolean keepJsDups) { Assert.notNull(name); logger.debug("Looking up beans for {}", name); final Collection<FactoryHandle> handles = handlesByName.get(name); final Collection<SyncBeanDef<?>> runtimeBeanDefs = runtimeBeanDefsByName.get(name); final JsArray<JsTypeProvider<?>> jsProviders = getJsProviders(name); final Set<String> beanDefFactoryNames = new HashSet<>(); final Collection beanDefs = new ArrayList<SyncBeanDef<Object>>(handles.size()+runtimeBeanDefs.size()+jsProviders.length()); beanDefs.addAll(runtimeBeanDefs); for (final FactoryHandle handle : handles) { if (handle.isAvailableByLookup()) { beanDefs.add(new IOCBeanDefImplementation<>(handle, this.<Object>getType(name, handle, handle.getActualType()))); beanDefFactoryNames.add(handle.getFactoryName()); } } for (final JsTypeProvider<?> provider : JsArray.iterable(jsProviders)) { logger.debug("Found JS provider for name {} from factory {}", provider.getName(), provider.getFactoryName()); if (keepJsDups || provider.getFactoryName() == null || !beanDefFactoryNames.contains(provider.getFactoryName())) { logger.debug("Keeping JS provider for name {} from factory {}", provider.getName(), provider.getFactoryName()); beanDefs.add(new JsTypeBeanDefImplementation(provider, name)); } else { logger.debug("Rejecting duplicate JS provider for name {} from factory {}", provider.getName(), provider.getFactoryName()); } } logger.debug("Looked up {} beans: {}", beanDefs.size(), beanDefs); return beanDefs; }
@Override public T newInstance() { return contextManager.getNewInstance(handle.getFactoryName()); }
@Override public void addFactory(final Factory<?> factory) { final Context context = getContextForScope(factory.getHandle().getScope()); context.registerFactory(factory); contextsByFactoryName.put(factory.getHandle().getFactoryName(), context); factory.init(context); }
@SuppressWarnings("unchecked") @Override public Class<T> getBeanClass() { return (Class<T>) handle.getActualType(); }
@Override public boolean isAssignableTo(final Class<?> type) { return handle.getAssignableTypes().contains(type); } }
@Override public Set<Annotation> getQualifiers() { if (qualifiers == null) { qualifiers = new HashSet<>(handle.getQualifiers()); } return qualifiers; }
@Override public String getName() { return handle.getBeanName(); }
private Collection<FactoryHandle> addFactories() { final Collection<FactoryHandle> eager = new ArrayList<>(); logger.debug("Adding factories..."); final long start = System.currentTimeMillis(); final Collection<FactoryHandle> allFactoryHandles = contextManager.getAllFactoryHandles(); for (final FactoryHandle handle : allFactoryHandles) { if (handle.isEager()) { eager.add(handle); } addFactory(handle); } final long duration = System.currentTimeMillis() - start; logger.debug("Added {} factories in {}ms.", allFactoryHandles.size(), duration); return eager; }
@Override public boolean isActivated() { final Class<? extends BeanActivator> activatorType = handle.getBeanActivatorType(); if (activatorType == null) { return true; } else { final BeanActivator activator = lookupBean(activatorType).getInstance(); return activator.isActivated(); } }
@Override public <T> void registerFactory(final Factory<T> factory) { factories.put(factory.getHandle().getFactoryName(), factory); }
@Override public <T> T getActiveNonProxiedInstance(final String factoryName) { if (hasActiveInstance(factoryName)) { return getActiveInstance(factoryName); } else if (isCurrentlyCreatingActiveInstance(factoryName)) { final Factory<T> factory = this.<T>getFactory(factoryName); final T incomplete = factory.getIncompleteInstance(); if (incomplete == null) { throw new RuntimeException("Could not obtain an incomplete instance of " + factory.getHandle().getActualType().getName() + " to break a circular injection."); } else { logger.warn("An incomplete " + factory.getHandle().getActualType() + " was required to break a circular injection."); return incomplete; } } else { return createNewUnproxiedInstance(factoryName); } }
@SuppressWarnings("unchecked") private <T> Class<T> getType(final String typeName, final FactoryHandle handle, final Class<?> defaultType) { for (final Class<?> type : handle.getAssignableTypes()) { if (type.getName().equals(typeName)) { return (Class<T>) type; } } return (Class<T>) defaultType; }
@Override public boolean matches(final Set<Annotation> annotations) { return QualifierUtil.matches(annotations, handle.getQualifiers()); }
@SuppressWarnings({ "rawtypes", "unchecked" }) @Override public void registerAsyncBean(final FactoryHandle handle, final FactoryLoader<?> future) { final String beanName; if (handle.getBeanName() != null) { beanName = handle.getBeanName(); } else { beanName = handle.getActualType().getName(); } typeNamesByName.put(beanName, handle.getActualType().getName()); final UnloadedFactory unloaded = new UnloadedFactory(handle, future); for (final Class<?> assignable : handle.getAssignableTypes()) { unloadedByTypeName.put(assignable.getName(), unloaded); } unloadedByFactoryName.put(handle.getFactoryName(), unloaded); }
@SuppressWarnings({ "unchecked", "rawtypes" }) private <T> void addUnloadedBeans(final Collection<AsyncBeanDef> beans, final Class<T> type, final String typeName, final Annotation... qualifiers) { final Collection<UnloadedFactory<?>> unloadedCandidates = unloadedByTypeName.get(typeName); final Collection<Annotation> allOf = Arrays.asList(qualifiers); for (final UnloadedFactory unloaded : unloadedCandidates) { if (QualifierUtil.matches(allOf, unloaded.getHandle().getQualifiers())) { final Class<T> beanType = (Class<T>) (type != null ? type : unloaded.getHandle().getActualType()); beans.add(unloaded.createBeanDef(beanType)); } } }
private Collection<UnloadedFactory<?>> getUnloadedAsyncDependencies() { final Deque<UnloadedFactory<?>> unloadedDeps = new LinkedList<>(); final Queue<String> bfsQueue = new LinkedList<>(asyncDependencies); final Set<String> visited = new HashSet<>(); visited.add(handle.getFactoryName()); while (bfsQueue.size() > 0) { final String factoryName = bfsQueue.poll(); if (visited.contains(factoryName)) { continue; } final UnloadedFactory<?> unloadedDep = unloadedByFactoryName.get(factoryName); if (unloadedDep != null && !unloadedDep.loaded) { unloadedDeps.addFirst(unloadedDep); visited.add(factoryName); for (final String dependentFactoryName : unloadedDep.asyncDependencies) { bfsQueue.add(dependentFactoryName); } } } return unloadedDeps; }