Search in sources :

Example 1 with ServiceInterfaceAnnotation

use of org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation in project controller by opendaylight.

the class InterfacesHelper method getServiceInterfaces.

/**
 * Get all implemented interfaces that have
 * {@link org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation}
 * annotation.
 *
 * @param configBeanClass
 *            config bean class
 * @return set containing classes
 */
public static Set<Class<?>> getServiceInterfaces(final Class<? extends Module> configBeanClass) {
    Set<Class<?>> allInterfaces = getAllInterfaces(configBeanClass);
    Set<Class<?>> result = new HashSet<>();
    for (Class<?> clazz : allInterfaces) {
        if (AbstractServiceInterface.class.isAssignableFrom(clazz)) {
            ServiceInterfaceAnnotation annotation = clazz.getAnnotation(ServiceInterfaceAnnotation.class);
            if (annotation != null) {
                result.add(clazz);
            }
        }
    }
    return result;
}
Also used : ServiceInterfaceAnnotation(org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation) HashSet(java.util.HashSet)

Example 2 with ServiceInterfaceAnnotation

use of org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation in project controller by opendaylight.

the class ConfigRegistryImpl method secondPhaseCommit.

@GuardedBy("configTransactionLock")
private CommitStatus secondPhaseCommit(final ConfigTransactionControllerInternal configTransactionController, final CommitInfo commitInfo, final ConfigTransactionLookupRegistry txLookupRegistry) {
    // (hopefully) runtime beans
    for (DestroyedModule toBeDestroyed : commitInfo.getDestroyedFromPreviousTransactions()) {
        // closes instance (which should close
        // runtime jmx registrator),
        // also closes osgi registration and ModuleJMXRegistrator
        // registration
        toBeDestroyed.close();
        currentConfig.remove(toBeDestroyed.getIdentifier());
    }
    // set RuntimeBeanRegistrators on beans implementing
    // RuntimeBeanRegistratorAwareModule
    Map<ModuleIdentifier, RootRuntimeBeanRegistratorImpl> runtimeRegistrators = new HashMap<>();
    for (ModuleInternalTransactionalInfo entry : commitInfo.getCommitted().values()) {
        // set runtime jmx registrator if required
        Module module = entry.getProxiedModule();
        RootRuntimeBeanRegistratorImpl runtimeBeanRegistrator = null;
        if (module instanceof RuntimeBeanRegistratorAwareModule) {
            if (entry.hasOldModule()) {
                if (module.canReuse(entry.getOldInternalInfo().getReadableModule().getModule())) {
                    runtimeBeanRegistrator = entry.getOldInternalInfo().getRuntimeBeanRegistrator();
                    ((RuntimeBeanRegistratorAwareModule) module).setRuntimeBeanRegistrator(runtimeBeanRegistrator);
                } else {
                    runtimeBeanRegistrator = baseJMXRegistrator.createRuntimeBeanRegistrator(entry.getIdentifier());
                    entry.getOldInternalInfo().getRuntimeBeanRegistrator().close();
                    ((RuntimeBeanRegistratorAwareModule) module).setRuntimeBeanRegistrator(runtimeBeanRegistrator);
                }
            } else {
                runtimeBeanRegistrator = baseJMXRegistrator.createRuntimeBeanRegistrator(entry.getIdentifier());
                ((RuntimeBeanRegistratorAwareModule) module).setRuntimeBeanRegistrator(runtimeBeanRegistrator);
            }
        }
        // save it to info so it is accessible afterwards
        if (runtimeBeanRegistrator != null) {
            runtimeRegistrators.put(entry.getIdentifier(), runtimeBeanRegistrator);
        }
    }
    // can register runtime beans
    List<ModuleIdentifier> orderedModuleIdentifiers = configTransactionController.secondPhaseCommit();
    txLookupRegistry.close();
    configTransactionController.close();
    // copy configuration to read only mode
    List<ObjectName> newInstances = new LinkedList<>();
    List<ObjectName> reusedInstances = new LinkedList<>();
    List<ObjectName> recreatedInstances = new LinkedList<>();
    Map<Module, ModuleInternalInfo> newConfigEntries = new HashMap<>();
    int orderingIdx = 0;
    for (ModuleIdentifier moduleIdentifier : orderedModuleIdentifiers) {
        LOG.trace("Registering {}", moduleIdentifier);
        ModuleInternalTransactionalInfo entry = commitInfo.getCommitted().get(moduleIdentifier);
        if (entry == null) {
            throw new NullPointerException("Module not found " + moduleIdentifier);
        }
        ObjectName primaryReadOnlyON = ObjectNameUtil.createReadOnlyModuleON(moduleIdentifier);
        // determine if current instance was recreated or reused or is new
        // rules for closing resources:
        // osgi registration - will be reused if possible.
        // module jmx registration - will be (re)created every time, needs
        // to be closed here
        // runtime jmx registration - should be taken care of by module
        // itself
        // instance - is closed only if it was destroyed
        ModuleJMXRegistrator newModuleJMXRegistrator = baseJMXRegistrator.createModuleJMXRegistrator();
        OsgiRegistration osgiRegistration = null;
        AutoCloseable instance = entry.getProxiedModule().getInstance();
        if (entry.hasOldModule()) {
            ModuleInternalInfo oldInternalInfo = entry.getOldInternalInfo();
            DynamicReadableWrapper oldReadableConfigBean = oldInternalInfo.getReadableModule();
            currentConfig.remove(entry.getIdentifier());
            // test if old instance == new instance
            if (oldReadableConfigBean.getInstance().equals(instance)) {
                // reused old instance:
                // wrap in readable dynamic mbean
                reusedInstances.add(primaryReadOnlyON);
                osgiRegistration = oldInternalInfo.getOsgiRegistration();
            } else {
                // recreated instance:
                // it is responsibility of module to call the old instance -
                // we just need to unregister configbean
                recreatedInstances.add(primaryReadOnlyON);
                // close old osgi registration
                oldInternalInfo.getOsgiRegistration().close();
            }
            // close old module jmx registrator
            oldInternalInfo.getModuleJMXRegistrator().close();
            // We no longer need old internal info. Clear it out, so we do not create a
            // serial leak evidenced
            // by BUG-4514. The reason is that modules retain their resolver, which retains
            // modules. If we retain
            // the old module, we would have the complete reconfiguration history held in
            // heap for no good reason.
            entry.clearOldInternalInfo();
        } else {
            // new instance:
            // wrap in readable dynamic mbean
            newInstances.add(primaryReadOnlyON);
        }
        Module realModule = entry.getRealModule();
        DynamicReadableWrapper newReadableConfigBean = new DynamicReadableWrapper(realModule, instance, moduleIdentifier, registryMBeanServer, configMBeanServer);
        // register to JMX
        try {
            newModuleJMXRegistrator.registerMBean(newReadableConfigBean, primaryReadOnlyON);
        } catch (final InstanceAlreadyExistsException e) {
            throw new IllegalStateException("Possible code error, already registered:" + primaryReadOnlyON, e);
        }
        // register services to OSGi
        Map<ServiceInterfaceAnnotation, String> annotationMapping = configTransactionController.getWritableRegistry().findServiceInterfaces(moduleIdentifier);
        BundleContext bc = configTransactionController.getModuleFactoryBundleContext(entry.getModuleFactory().getImplementationName());
        if (osgiRegistration == null) {
            osgiRegistration = beanToOsgiServiceManager.registerToOsgi(newReadableConfigBean.getInstance(), moduleIdentifier, bc, annotationMapping);
        } else {
            osgiRegistration.updateRegistrations(annotationMapping, bc, instance);
        }
        RootRuntimeBeanRegistratorImpl runtimeBeanRegistrator = runtimeRegistrators.get(entry.getIdentifier());
        ModuleInternalInfo newInfo = new ModuleInternalInfo(entry.getIdentifier(), newReadableConfigBean, osgiRegistration, runtimeBeanRegistrator, newModuleJMXRegistrator, orderingIdx, entry.isDefaultBean(), entry.getModuleFactory(), entry.getBundleContext());
        newConfigEntries.put(realModule, newInfo);
        orderingIdx++;
    }
    currentConfig.addAll(newConfigEntries.values());
    // update version
    version = configTransactionController.getVersion();
    // switch readable Service Reference Registry
    synchronized (readableSRRegistryLock) {
        readableSRRegistry.close();
        readableSRRegistry = ServiceReferenceRegistryImpl.createSRReadableRegistry(configTransactionController.getWritableRegistry(), this, baseJMXRegistrator);
    }
    return new CommitStatus(newInstances, reusedInstances, recreatedInstances);
}
Also used : ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) HashMap(java.util.HashMap) ServiceInterfaceAnnotation(org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation) DynamicReadableWrapper(org.opendaylight.controller.config.manager.impl.dynamicmbean.DynamicReadableWrapper) CommitStatus(org.opendaylight.controller.config.api.jmx.CommitStatus) ModuleIdentifier(org.opendaylight.controller.config.api.ModuleIdentifier) OsgiRegistration(org.opendaylight.controller.config.manager.impl.osgi.BeanToOsgiServiceManager.OsgiRegistration) ModuleJMXRegistrator(org.opendaylight.controller.config.manager.impl.jmx.ModuleJMXRegistrator) DestroyedModule(org.opendaylight.controller.config.manager.impl.dependencyresolver.DestroyedModule) InstanceAlreadyExistsException(javax.management.InstanceAlreadyExistsException) RuntimeBeanRegistratorAwareModule(org.opendaylight.controller.config.api.RuntimeBeanRegistratorAwareModule) ModuleInternalTransactionalInfo(org.opendaylight.controller.config.manager.impl.dependencyresolver.ModuleInternalTransactionalInfo) LinkedList(java.util.LinkedList) ObjectName(javax.management.ObjectName) DestroyedModule(org.opendaylight.controller.config.manager.impl.dependencyresolver.DestroyedModule) RuntimeBeanRegistratorAwareModule(org.opendaylight.controller.config.api.RuntimeBeanRegistratorAwareModule) Module(org.opendaylight.controller.config.spi.Module) RootRuntimeBeanRegistratorImpl(org.opendaylight.controller.config.manager.impl.jmx.RootRuntimeBeanRegistratorImpl) BundleContext(org.osgi.framework.BundleContext) GuardedBy(javax.annotation.concurrent.GuardedBy)

Example 3 with ServiceInterfaceAnnotation

use of org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation in project controller by opendaylight.

the class ConfigTransactionControllerImpl method processDefaultBeans.

private synchronized void processDefaultBeans(final List<ModuleFactory> lastListOfFactories) {
    transactionStatus.checkNotCommitStarted();
    transactionStatus.checkNotAborted();
    Set<ModuleFactory> oldSet = new HashSet<>(lastListOfFactories);
    Set<ModuleFactory> newSet = new HashSet<>(factoriesHolder.getModuleFactories());
    List<ModuleFactory> toBeAdded = new ArrayList<>();
    List<ModuleFactory> toBeRemoved = new ArrayList<>();
    for (ModuleFactory moduleFactory : factoriesHolder.getModuleFactories()) {
        if (!oldSet.contains(moduleFactory)) {
            toBeAdded.add(moduleFactory);
        }
    }
    for (ModuleFactory moduleFactory : lastListOfFactories) {
        if (!newSet.contains(moduleFactory)) {
            toBeRemoved.add(moduleFactory);
        }
    }
    // add default modules
    for (ModuleFactory moduleFactory : toBeAdded) {
        BundleContext bundleContext = getModuleFactoryBundleContext(moduleFactory.getImplementationName());
        Set<? extends Module> defaultModules = moduleFactory.getDefaultModules(dependencyResolverManager, bundleContext);
        for (Module module : defaultModules) {
            // ensure default module to be registered to jmx even if its module factory does
            // not use dependencyResolverFactory
            DependencyResolver dependencyResolver = dependencyResolverManager.getOrCreate(module.getIdentifier());
            final ObjectName objectName;
            try {
                boolean defaultBean = true;
                objectName = putConfigBeanToJMXAndInternalMaps(module.getIdentifier(), module, moduleFactory, null, dependencyResolver, defaultBean, bundleContext);
            } catch (final InstanceAlreadyExistsException e) {
                throw new IllegalStateException(e);
            }
            // register default module as every possible service
            final Set<ServiceInterfaceAnnotation> serviceInterfaceAnnotations = InterfacesHelper.getServiceInterfaceAnnotations(moduleFactory);
            for (String qname : InterfacesHelper.getQNames(serviceInterfaceAnnotations)) {
                try {
                    saveServiceReference(qname, module.getIdentifier().getInstanceName(), objectName);
                } catch (final InstanceNotFoundException e) {
                    throw new IllegalStateException("Unable to register default module instance " + module + " as a service of " + qname, e);
                }
            }
        }
    }
    // remove modules belonging to removed factories
    for (ModuleFactory removedFactory : toBeRemoved) {
        List<ModuleIdentifier> modulesOfRemovedFactory = dependencyResolverManager.findAllByFactory(removedFactory);
        for (ModuleIdentifier name : modulesOfRemovedFactory) {
            // remove service refs
            final ModuleFactory moduleFactory = dependencyResolverManager.findModuleInternalTransactionalInfo(name).getModuleFactory();
            final Set<ServiceInterfaceAnnotation> serviceInterfaceAnnotations = InterfacesHelper.getServiceInterfaceAnnotations(moduleFactory);
            for (String qname : InterfacesHelper.getQNames(serviceInterfaceAnnotations)) {
                try {
                    removeServiceReference(qname, name.getInstanceName());
                } catch (final InstanceNotFoundException e) {
                    throw new IllegalStateException("Unable to UNregister default module instance " + name + " as a service of " + qname, e);
                }
            }
            // close module
            destroyModule(name);
        }
    }
}
Also used : InstanceAlreadyExistsException(javax.management.InstanceAlreadyExistsException) InstanceNotFoundException(javax.management.InstanceNotFoundException) ArrayList(java.util.ArrayList) ServiceInterfaceAnnotation(org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation) DependencyResolver(org.opendaylight.controller.config.api.DependencyResolver) ObjectName(javax.management.ObjectName) ModuleFactory(org.opendaylight.controller.config.spi.ModuleFactory) ModuleIdentifier(org.opendaylight.controller.config.api.ModuleIdentifier) AbstractModule(org.opendaylight.controller.config.spi.AbstractModule) Module(org.opendaylight.controller.config.spi.Module) HashSet(java.util.HashSet) BundleContext(org.osgi.framework.BundleContext)

Example 4 with ServiceInterfaceAnnotation

use of org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation in project controller by opendaylight.

the class ServiceReferenceRegistryImpl method getServiceInterfaceName.

@Override
public synchronized String getServiceInterfaceName(final String namespace, final String localName) {
    Map<String, ServiceInterfaceAnnotation> /* localName */
    ofNamespace = namespacesToAnnotations.get(namespace);
    if (ofNamespace == null) {
        LOG.error("Cannot find namespace {} in {}", namespace, namespacesToAnnotations);
        throw new IllegalArgumentException("Cannot find namespace " + namespace);
    }
    ServiceInterfaceAnnotation sia = ofNamespace.get(localName);
    if (sia == null) {
        LOG.error("Cannot find local name {} in namespace {}, found only {}", localName, namespace, ofNamespace);
        throw new IllegalArgumentException("Cannot find local name " + localName + " in namespace " + namespace);
    }
    return sia.value();
}
Also used : ServiceInterfaceAnnotation(org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation)

Example 5 with ServiceInterfaceAnnotation

use of org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation in project controller by opendaylight.

the class ServiceReferenceRegistryImpl method saveServiceReference.

private synchronized ObjectName saveServiceReference(final ServiceReference serviceReference, final ObjectName moduleON, final boolean skipChecks) throws InstanceNotFoundException {
    // make sure it is found
    if (!skipChecks) {
        lookupRegistry.checkConfigBeanExists(moduleON);
    }
    String factoryName = ObjectNameUtil.getFactoryName(moduleON);
    String instanceName = ObjectNameUtil.getInstanceName(moduleON);
    ModuleIdentifier moduleIdentifier = new ModuleIdentifier(factoryName, instanceName);
    // check that service interface name exist
    Set<String> serviceInterfaceQNames = factoryNamesToQNames.get(moduleIdentifier.getFactoryName());
    if (serviceInterfaceQNames == null) {
        LOG.error("Possible error in code: cannot find factoryName {} in {}, {}", moduleIdentifier.getFactoryName(), factoryNamesToQNames, moduleIdentifier);
        throw new IllegalStateException("Possible error in code: cannot find annotations of existing factory " + moduleIdentifier.getFactoryName());
    }
    // supplied serviceInterfaceName must exist in this collection
    if (!serviceInterfaceQNames.contains(serviceReference.getServiceInterfaceQName())) {
        LOG.error("Cannot find qName {} with factory name {}, found {}", serviceReference.getServiceInterfaceQName(), moduleIdentifier.getFactoryName(), serviceInterfaceQNames);
        throw new IllegalArgumentException("Cannot find service interface " + serviceReference.getServiceInterfaceQName() + " within factory " + moduleIdentifier.getFactoryName());
    }
    // create service reference object name, put to mBeans
    ObjectName result = getServiceON(serviceReference);
    Entry<ServiceReferenceMXBeanImpl, ServiceReferenceJMXRegistration> mxBeanEntry = managementBeans.get(serviceReference);
    if (mxBeanEntry == null) {
        // create dummy mx bean
        ServiceReferenceMXBeanImpl dummyMXBean = new ServiceReferenceMXBeanImpl(moduleON);
        ServiceReferenceJMXRegistration dummyMXBeanRegistration;
        try {
            dummyMXBeanRegistration = serviceReferenceRegistrator.registerMBean(dummyMXBean, result);
        } catch (final InstanceAlreadyExistsException e) {
            throw new IllegalStateException("Possible error in code. Cannot register " + result, e);
        }
        managementBeans.put(serviceReference, new SimpleImmutableEntry<>(dummyMXBean, dummyMXBeanRegistration));
    } else {
        // update
        mxBeanEntry.getKey().setCurrentImplementation(moduleON);
    }
    // save to refNames
    refNames.put(serviceReference, moduleIdentifier);
    Map<ServiceInterfaceAnnotation, String> /* service ref name */
    refNamesToAnnotations = modulesToServiceRef.computeIfAbsent(moduleIdentifier, k -> new HashMap<>());
    ServiceInterfaceAnnotation annotation = serviceQNamesToAnnotations.get(serviceReference.getServiceInterfaceQName());
    Preconditions.checkNotNull(annotation, "Possible error in code, cannot find annotation for " + serviceReference);
    refNamesToAnnotations.put(annotation, serviceReference.getRefName());
    return result;
}
Also used : ServiceReferenceMXBeanImpl(org.opendaylight.controller.config.manager.impl.jmx.ServiceReferenceMXBeanImpl) InstanceAlreadyExistsException(javax.management.InstanceAlreadyExistsException) ServiceInterfaceAnnotation(org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation) ObjectName(javax.management.ObjectName) ModuleIdentifier(org.opendaylight.controller.config.api.ModuleIdentifier) ServiceReferenceJMXRegistration(org.opendaylight.controller.config.manager.impl.jmx.ServiceReferenceRegistrator.ServiceReferenceJMXRegistration)

Aggregations

ServiceInterfaceAnnotation (org.opendaylight.controller.config.api.annotations.ServiceInterfaceAnnotation)7 HashSet (java.util.HashSet)4 InstanceAlreadyExistsException (javax.management.InstanceAlreadyExistsException)3 ObjectName (javax.management.ObjectName)3 ModuleIdentifier (org.opendaylight.controller.config.api.ModuleIdentifier)3 Module (org.opendaylight.controller.config.spi.Module)2 BundleContext (org.osgi.framework.BundleContext)2 ArrayList (java.util.ArrayList)1 HashMap (java.util.HashMap)1 LinkedList (java.util.LinkedList)1 ConcurrentHashMap (java.util.concurrent.ConcurrentHashMap)1 GuardedBy (javax.annotation.concurrent.GuardedBy)1 InstanceNotFoundException (javax.management.InstanceNotFoundException)1 DependencyResolver (org.opendaylight.controller.config.api.DependencyResolver)1 RuntimeBeanRegistratorAwareModule (org.opendaylight.controller.config.api.RuntimeBeanRegistratorAwareModule)1 AbstractServiceInterface (org.opendaylight.controller.config.api.annotations.AbstractServiceInterface)1 CommitStatus (org.opendaylight.controller.config.api.jmx.CommitStatus)1 DestroyedModule (org.opendaylight.controller.config.manager.impl.dependencyresolver.DestroyedModule)1 ModuleInternalTransactionalInfo (org.opendaylight.controller.config.manager.impl.dependencyresolver.ModuleInternalTransactionalInfo)1 DynamicReadableWrapper (org.opendaylight.controller.config.manager.impl.dynamicmbean.DynamicReadableWrapper)1