X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?a=blobdiff_plain;f=opendaylight%2Fnetconf%2Fconfig-netconf-connector%2Fsrc%2Fmain%2Fjava%2Forg%2Fopendaylight%2Fcontroller%2Fnetconf%2Fconfignetconfconnector%2Fmapping%2Fconfig%2FServices.java;h=9767b3f0560cdeae5f51927a1275dec0e7f8f29f;hb=aacafb25b08def6ea9f2537356da418805c80ba9;hp=7e4b6c2c06a5040750f1a75510c747fdccead290;hpb=a92d9d6a21a0f6ca8d2153795721f500eaf29ee9;p=controller.git diff --git a/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/config/Services.java b/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/config/Services.java index 7e4b6c2c06..9767b3f056 100644 --- a/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/config/Services.java +++ b/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/config/Services.java @@ -8,154 +8,86 @@ package org.opendaylight.controller.netconf.confignetconfconnector.mapping.config; -import com.google.common.base.Function; -import com.google.common.base.Preconditions; -import com.google.common.collect.Maps; -import com.google.common.collect.Sets; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import javax.management.ObjectName; + +import org.opendaylight.controller.config.api.jmx.ObjectNameUtil; +import org.opendaylight.controller.netconf.confignetconfconnector.mapping.attributes.fromxml.ObjectNameAttributeReadingStrategy; import org.opendaylight.controller.netconf.util.xml.XmlElement; import org.opendaylight.controller.netconf.util.xml.XmlNetconfConstants; import org.opendaylight.controller.netconf.util.xml.XmlUtil; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import org.w3c.dom.Document; import org.w3c.dom.Element; -import javax.annotation.Nullable; -import javax.management.ObjectName; -import java.util.Collection; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Set; -import java.util.regex.Matcher; -import java.util.regex.Pattern; +import com.google.common.base.Optional; +import com.google.common.base.Preconditions; +import com.google.common.collect.Maps; public final class Services { + private static final Logger logger = LoggerFactory.getLogger(Services.class); + private static final String PROVIDER_KEY = "provider"; private static final String NAME_KEY = "name"; public static final String TYPE_KEY = "type"; public static final String SERVICE_KEY = "service"; - private long suffix = 1; - - private final Map instanceToRef = Maps.newHashMap(); - private final Map> serviceNameToRefNameToInstance = Maps + private final Map>> namespaceToServiceNameToRefNameToInstance = Maps .newHashMap(); - public String addServiceEntry(String serviceName, ObjectName on) { - - String moduleName = on.getKeyProperty("moduleFactoryName"); - String instanceName = on.getKeyProperty("instanceName"); - - return addServiceEntry(serviceName, moduleName, instanceName); - } - - public String addServiceEntry(String serviceName, String moduleName, String instanceName) { - ServiceInstance serviceInstance = new ServiceInstance(moduleName, instanceName); - serviceInstance.setServiceName(serviceName); - - String refName = instanceToRef.get(serviceInstance); - - Map refNameToInstance = serviceNameToRefNameToInstance.get(serviceName); - if (refNameToInstance == null) { - refNameToInstance = Maps.newHashMap(); - serviceNameToRefNameToInstance.put(serviceName, refNameToInstance); - } - - if (refName != null) { - if (serviceNameToRefNameToInstance.get(serviceName).containsKey(moduleName) == false) { - refNameToInstance.put(refName, serviceInstance); - } - return refName; - } else { - refName = "ref_" + instanceName; - - final Set refNamesAsSet = toSet(instanceToRef.values()); - if (refNamesAsSet.contains(refName)) { - refName = findAvailableRefName(refName, refNamesAsSet); - } - - instanceToRef.put(serviceInstance, refName); - refNameToInstance.put(refName, serviceInstance); - - return refName; - } - } - - private Set toSet(Collection values) { - Set refNamesAsSet = Sets.newHashSet(); - - for (String refName : values) { - boolean resultAdd = refNamesAsSet.add(refName); - Preconditions.checkState(resultAdd, - "Error occurred building services element, reference name {} was present twice", refName); - } - - return refNamesAsSet; + /** + * + */ + public Map>> getNamespaceToServiceNameToRefNameToInstance() { + return namespaceToServiceNameToRefNameToInstance; } - public ServiceInstance getByServiceAndRefName(String serviceName, String refName) { - Map refNameToInstance = serviceNameToRefNameToInstance.get(serviceName); - Preconditions.checkArgument(refNameToInstance != null, "No serviceInstances mapped to " + serviceName + " , " - + serviceNameToRefNameToInstance.keySet()); - - ServiceInstance serviceInstance = refNameToInstance.get(refName); - Preconditions.checkArgument(serviceInstance != null, "No serviceInstance mapped to " + refName - + " under service name " + serviceName + " , " + refNameToInstance.keySet()); - return serviceInstance; - } - - // TODO hide getMappedServices, call it explicitly in toXml - - public Map> getMappedServices() { - Map> retVal = Maps.newHashMap(); + private static Services resolveServices(Map>> mappedServices) { + Services tracker = new Services(); - for (String serviceName : serviceNameToRefNameToInstance.keySet()) { + for (Entry>> namespaceEntry : mappedServices.entrySet()) { + String namespace = namespaceEntry.getKey(); - Map innerRetVal = Maps.transformValues(serviceNameToRefNameToInstance.get(serviceName), - new Function() { - @Nullable - @Override - public String apply(@Nullable ServiceInstance serviceInstance) { - return serviceInstance.toString(); - } - }); - retVal.put(serviceName, innerRetVal); - } + for (Entry> serviceEntry : namespaceEntry.getValue().entrySet()) { - return retVal; - } + String serviceName = serviceEntry.getKey(); + for (Entry refEntry : serviceEntry.getValue().entrySet()) { - // TODO hide resolveServices, call it explicitly in fromXml + Map> namespaceToServices = tracker.namespaceToServiceNameToRefNameToInstance.get(namespace); + if (namespaceToServices == null) { + namespaceToServices = Maps.newHashMap(); + tracker.namespaceToServiceNameToRefNameToInstance.put(namespace, namespaceToServices); + } - public static Services resolveServices(Map> mappedServices) { - Services tracker = new Services(); + Map refNameToInstance = namespaceToServices + .get(serviceName); + if (refNameToInstance == null) { + refNameToInstance = Maps.newHashMap(); + namespaceToServices.put(serviceName, refNameToInstance); + } - for (Entry> serviceEntry : mappedServices.entrySet()) { + String refName = refEntry.getKey(); - String serviceName = serviceEntry.getKey(); - for (Entry refEntry : serviceEntry.getValue().entrySet()) { + ServiceInstance serviceInstance = ServiceInstance.fromString(refEntry.getValue()); + refNameToInstance.put(refName, serviceInstance); - Map refNameToInstance = tracker.serviceNameToRefNameToInstance - .get(serviceName); - if (refNameToInstance == null) { - refNameToInstance = Maps.newHashMap(); - tracker.serviceNameToRefNameToInstance.put(serviceName, refNameToInstance); } - - String refName = refEntry.getKey(); - Preconditions.checkState(false == refNameToInstance.containsKey(refName), - "Duplicate reference name to service " + refName + " under service " + serviceName); - ServiceInstance serviceInstance = ServiceInstance.fromString(refEntry.getValue()); - refNameToInstance.put(refName, serviceInstance); - - tracker.instanceToRef.put(serviceInstance, refEntry.getKey()); } } return tracker; } - public static Map> fromXml(XmlElement xml) { - Map> retVal = Maps.newHashMap(); + // TODO support edit strategies on services + + public static Services fromXml(XmlElement xml) { + Map>> retVal = Maps.newHashMap(); List services = xml.getChildElements(SERVICE_KEY); xml.checkUnrecognisedElements(services); @@ -163,10 +95,20 @@ public final class Services { for (XmlElement service : services) { XmlElement typeElement = service.getOnlyChildElement(TYPE_KEY); - String serviceName = typeElement.getTextContent(); + Entry prefixNamespace = typeElement.findNamespaceOfTextContent(); + + Preconditions.checkState(prefixNamespace.getKey()!=null && prefixNamespace.getKey().equals("") == false, "Type attribute was not prefixed"); + + Map> namespaceToServices = retVal.get(prefixNamespace.getValue()); + if(namespaceToServices == null) { + namespaceToServices = Maps.newHashMap(); + retVal.put(prefixNamespace.getValue(), namespaceToServices); + } + + String serviceName = ObjectNameAttributeReadingStrategy.checkPrefixAndExtractServiceName(typeElement, prefixNamespace); Map innerMap = Maps.newHashMap(); - retVal.put(serviceName, innerMap); + namespaceToServices.put(serviceName, innerMap); List instances = service.getChildElements(XmlNetconfConstants.INSTANCE_KEY); service.checkUnrecognisedElements(instances, typeElement); @@ -184,42 +126,36 @@ public final class Services { } } - return retVal; + return resolveServices(retVal); } - private String findAvailableRefName(String refName, Set refNamesAsSet) { - String intitialRefName = refName; + public static Element toXml(ServiceRegistryWrapper serviceRegistryWrapper, Document document) { + Element root = XmlUtil.createElement(document, XmlNetconfConstants.SERVICES_KEY, Optional.of(XmlNetconfConstants.URN_OPENDAYLIGHT_PARAMS_XML_NS_YANG_CONTROLLER_CONFIG)); - while (true) { - refName = intitialRefName + "_" + suffix++; - if (refNamesAsSet.contains(refName) == false) - return refName; - } - } + Map>> mappedServices = serviceRegistryWrapper.getMappedServices(); + for (String namespace : mappedServices.keySet()) { - public Element toXml(Map> mappedServices, Document document) { - Element root = document.createElement(XmlNetconfConstants.SERVICES_KEY); - XmlUtil.addNamespaceAttr(root, XmlNetconfConstants.URN_OPENDAYLIGHT_PARAMS_XML_NS_YANG_CONTROLLER_CONFIG); + for (Entry> serviceEntry : mappedServices.get(namespace).entrySet()) { + Element serviceElement = XmlUtil.createElement(document, SERVICE_KEY, Optional.absent()); + root.appendChild(serviceElement); - for (Entry> serviceEntry : mappedServices.entrySet()) { - Element serviceElement = document.createElement(SERVICE_KEY); - root.appendChild(serviceElement); + Element typeElement = XmlUtil.createPrefixedTextElement(document, XmlUtil.createPrefixedValue(XmlNetconfConstants.PREFIX, TYPE_KEY), XmlNetconfConstants.PREFIX, + serviceEntry.getKey(), Optional.of(namespace)); + serviceElement.appendChild(typeElement); - Element typeElement = XmlUtil.createTextElement(document, TYPE_KEY, serviceEntry.getKey()); - serviceElement.appendChild(typeElement); + for (Entry instanceEntry : serviceEntry.getValue().entrySet()) { + Element instanceElement = XmlUtil.createElement(document, XmlNetconfConstants.INSTANCE_KEY, Optional.absent()); + serviceElement.appendChild(instanceElement); - for (Entry instanceEntry : serviceEntry.getValue().entrySet()) { - Element instanceElement = document.createElement(XmlNetconfConstants.INSTANCE_KEY); - serviceElement.appendChild(instanceElement); + Element nameElement = XmlUtil.createTextElement(document, NAME_KEY, instanceEntry.getKey(), Optional.absent()); + instanceElement.appendChild(nameElement); - Element nameElement = XmlUtil.createTextElement(document, NAME_KEY, instanceEntry.getKey()); - instanceElement.appendChild(nameElement); - - Element providerElement = XmlUtil.createTextElement(document, PROVIDER_KEY, instanceEntry.getValue()); - instanceElement.appendChild(providerElement); + Element providerElement = XmlUtil.createTextElement(document, PROVIDER_KEY, instanceEntry.getValue(), Optional.absent()); + instanceElement.appendChild(providerElement); + } } - } + } return root; } @@ -232,8 +168,13 @@ public final class Services { public static ServiceInstance fromString(String instanceId) { instanceId = instanceId.trim(); Matcher matcher = p.matcher(instanceId); + if(matcher.matches() == false) { + matcher = pDeprecated.matcher(instanceId); + } + Preconditions.checkArgument(matcher.matches(), "Unexpected format for provider, expected " + p.toString() - + " but was " + instanceId); + + " or " + pDeprecated.toString() + " but was " + instanceId); + String factoryName = matcher.group(1); String instanceName = matcher.group(2); return new ServiceInstance(factoryName, instanceName); @@ -258,16 +199,25 @@ public final class Services { return instanceName; } - private static final String blueprint = "/" + XmlNetconfConstants.CONFIG_KEY + "/" + private static final String blueprint = "/" + XmlNetconfConstants.MODULES_KEY + "/" + XmlNetconfConstants.MODULE_KEY + "[" - + XmlNetconfConstants.NAME_KEY + "='%s']/" + XmlNetconfConstants.INSTANCE_KEY + "[" + + XmlNetconfConstants.TYPE_KEY + "='%s'][" + XmlNetconfConstants.NAME_KEY + "='%s']"; - private static final String blueprintR = "/" + XmlNetconfConstants.CONFIG_KEY + "/" + // TODO unify with xpath in RuntimeRpc + + // Previous version of xpath, needs to be supported for backwards compatibility (persisted configs by config-persister) + private static final String blueprintRDeprecated = "/" + XmlNetconfConstants.CONFIG_KEY + "/" + XmlNetconfConstants.MODULES_KEY + "/" + XmlNetconfConstants.MODULE_KEY + "\\[" + XmlNetconfConstants.NAME_KEY + "='%s'\\]/" + XmlNetconfConstants.INSTANCE_KEY + "\\[" + XmlNetconfConstants.NAME_KEY + "='%s'\\]"; + private static final String blueprintR = "/" + + XmlNetconfConstants.MODULES_KEY + "/" + XmlNetconfConstants.MODULE_KEY + "\\[" + + XmlNetconfConstants.TYPE_KEY + "='%s'\\]\\[" + + XmlNetconfConstants.NAME_KEY + "='%s'\\]"; + + private static final Pattern pDeprecated = Pattern.compile(String.format(blueprintRDeprecated, "(.+)", "(.+)")); private static final Pattern p = Pattern.compile(String.format(blueprintR, "(.+)", "(.+)")); @Override @@ -306,6 +256,13 @@ public final class Services { return true; } + public ObjectName getObjectName(String transactionName) { + return ObjectNameUtil.createTransactionModuleON(transactionName, moduleName, instanceName); + } + + public static ServiceInstance fromObjectName(ObjectName on) { + return new ServiceInstance(ObjectNameUtil.getFactoryName(on), ObjectNameUtil.getInstanceName(on)); + } } }