From 23ec2c1ab1e9266029437be0818101efbc74450e Mon Sep 17 00:00:00 2001 From: Maros Marsalek Date: Thu, 12 Dec 2013 11:12:11 +0100 Subject: [PATCH] Added xml storage adapter bundle fragments for config persister. File and Directory based xml adapters are now available. Only File xml adapter is used so far to persist current configuration. Directory based persister is still using plain text to keep backwards compatibility. Change-Id: If1a83701ce23d36313c943e9fe49bd4e704afe27 Signed-off-by: Maros Marsalek --- .../storage/directory/DirectoryPersister.java | 2 +- .../pom.xml | 115 +++++++++++ .../directory/xml/XmlDirectoryPersister.java | 108 ++++++++++ .../xml/XmlDirectoryStorageAdapter.java | 39 ++++ .../xml/DirectoryStorageAdapterTest.java | 88 ++++++++ .../resources/oneFile/controller.config.xml | 10 + .../resources/twoFiles/controller.config1.xml | 10 + .../resources/twoFiles/controller.config2.xml | 10 + .../config-persister-file-xml-adapter/pom.xml | 87 ++++++++ .../file/xml/XmlFileStorageAdapter.java | 149 ++++++++++++++ .../file/xml/model/CapabilityHandler.java | 47 +++++ .../storage/file/xml/model/Config.java | 109 ++++++++++ .../file/xml/model/ConfigSnapshot.java | 63 ++++++ .../file/xml/model/PersistException.java | 15 ++ .../file/xml/model/SnapshotHandler.java | 47 +++++ .../file/xml/FileStorageAdapterTest.java | 188 ++++++++++++++++++ opendaylight/config/pom.xml | 2 + .../distribution/opendaylight/pom.xml | 20 +- .../main/resources/configuration/config.ini | 12 +- .../attributes/AttributesConstants.java | 11 +- .../mapping/config/Services.java | 6 +- .../NetconfMappingTest.java | 14 +- .../netconf/config-persister-impl/pom.xml | 8 +- .../persist/impl/PersisterAggregator.java | 2 +- .../persist/impl/PersisterAggregatorTest.java | 4 +- .../src/test/resources/test2.properties | 4 +- .../src/test/resources/test3.properties | 2 +- 27 files changed, 1144 insertions(+), 28 deletions(-) create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/pom.xml create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryPersister.java create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryStorageAdapter.java create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/directory/xml/DirectoryStorageAdapterTest.java create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/oneFile/controller.config.xml create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config1.xml create mode 100644 opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config2.xml create mode 100644 opendaylight/config/config-persister-file-xml-adapter/pom.xml create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/XmlFileStorageAdapter.java create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/CapabilityHandler.java create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/Config.java create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/ConfigSnapshot.java create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/PersistException.java create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/SnapshotHandler.java create mode 100644 opendaylight/config/config-persister-file-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/file/xml/FileStorageAdapterTest.java diff --git a/opendaylight/config/config-persister-directory-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/DirectoryPersister.java b/opendaylight/config/config-persister-directory-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/DirectoryPersister.java index 39595edb0b..a123eb981e 100644 --- a/opendaylight/config/config-persister-directory-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/DirectoryPersister.java +++ b/opendaylight/config/config-persister-directory-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/DirectoryPersister.java @@ -139,7 +139,7 @@ class MyLineProcessor implements com.google.common.io.LineProcessor { } private void checkFileConsistency(){ - checkState(inCapabilities, "File {} is missing delimiters in this order: {}", fileNameForReporting, + checkState(inCapabilities, "File %s is missing delimiters in this order: %s", fileNameForReporting, Arrays.asList(DirectoryPersister.MODULES_START, DirectoryPersister.SERVICES_START, DirectoryPersister.CAPABILITIES_START)); diff --git a/opendaylight/config/config-persister-directory-xml-adapter/pom.xml b/opendaylight/config/config-persister-directory-xml-adapter/pom.xml new file mode 100644 index 0000000000..b2ea632834 --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/pom.xml @@ -0,0 +1,115 @@ + + + 4.0.0 + + config-subsystem + org.opendaylight.controller + 0.2.3-SNAPSHOT + .. + + config-persister-directory-xml-adapter + ${project.artifactId} + bundle + + + + + ${project.groupId} + config-persister-api + + + org.apache.commons + commons-lang3 + + + com.google.guava + guava + + + org.opendaylight.controller + config-persister-file-xml-adapter + ${config.version} + + + + org.eclipse.persistence + org.eclipse.persistence.moxy + + + org.eclipse.persistence + org.eclipse.persistence.core + + + + org.slf4j + slf4j-api + + + commons-io + commons-io + + + + + org.opendaylight.bgpcep + mockito-configuration + test + + + + + + + + + org.codehaus.groovy.maven + gmaven-plugin + + + generate-sources + + execute + + + + System.setProperty("osgiversion", "${project.version}".replace('-', '.')) + + + + + + + org.apache.felix + maven-bundle-plugin + + + ${project.groupId}.config-persister-impl;bundle-version=${osgiversion} + + org.opendaylight.controller.config.persister.storage.adapter + + + com.google.common.base, + com.google.common.io, + org.apache.commons.io, + org.opendaylight.controller.config.persist.api, + org.slf4j, + com.google.common.collect, + javax.xml.bind, + javax.xml.bind.annotation, + javax.xml.transform, + javax.xml.transform.stream, + org.eclipse.persistence.jaxb, + org.apache.commons.lang3 + + + org.opendaylight.controller.config.persist.storage.file.xml.model, + + + + + + + + diff --git a/opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryPersister.java b/opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryPersister.java new file mode 100644 index 0000000000..f6f6de9fd5 --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryPersister.java @@ -0,0 +1,108 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.config.persist.storage.directory.xml; + +import org.opendaylight.controller.config.persist.api.ConfigSnapshotHolder; +import org.opendaylight.controller.config.persist.api.Persister; +import org.opendaylight.controller.config.persist.storage.file.xml.model.ConfigSnapshot; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import javax.xml.bind.JAXBContext; +import javax.xml.bind.JAXBException; +import javax.xml.bind.Unmarshaller; +import java.io.File; +import java.io.IOException; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; +import java.util.SortedSet; + +import static com.google.common.base.Preconditions.checkArgument; + +public class XmlDirectoryPersister implements Persister { + private static final Logger logger = LoggerFactory.getLogger(XmlDirectoryPersister.class); + + private final File storage; + + public XmlDirectoryPersister(File storage) { + checkArgument(storage.exists() && storage.isDirectory(), "Storage directory does not exist: " + storage); + this.storage = storage; + } + + @Override + public void persistConfig(ConfigSnapshotHolder holder) throws IOException { + throw new UnsupportedOperationException("This adapter is read only. Please set readonly=true on " + getClass()); + } + + @Override + public List loadLastConfigs() throws IOException { + File[] filesArray = storage.listFiles(); + if (filesArray == null || filesArray.length == 0) { + return Collections.emptyList(); + } + List sortedFiles = new ArrayList<>(Arrays.asList(filesArray)); + Collections.sort(sortedFiles); + // combine all found files + logger.debug("Reading files in following order: {}", sortedFiles); + + List result = new ArrayList<>(); + for (File file : sortedFiles) { + logger.trace("Adding file '{}' to combined result", file); + ConfigSnapshotHolder h = fromXmlSnapshot(file); + result.add(h); + } + return result; + } + + private ConfigSnapshotHolder fromXmlSnapshot(File file) { + try { + JAXBContext jaxbContext = JAXBContext.newInstance(ConfigSnapshot.class); + Unmarshaller um = jaxbContext.createUnmarshaller(); + + return asHolder((ConfigSnapshot) um.unmarshal(file)); + } catch (JAXBException e) { + logger.warn("Unable to restore configuration snapshot from {}", file, e); + throw new IllegalStateException("Unable to restore configuration snapshot from " + file, e); + } + } + + private ConfigSnapshotHolder asHolder(final ConfigSnapshot unmarshalled) { + return new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + return unmarshalled.getConfigSnapshot(); + } + + @Override + public SortedSet getCapabilities() { + return unmarshalled.getCapabilities(); + } + + @Override + public String toString() { + return unmarshalled.toString(); + } + }; + } + + + @Override + public void close() { + + } + + @Override + public String toString() { + final StringBuffer sb = new StringBuffer("XmlDirectoryPersister{"); + sb.append("storage=").append(storage); + sb.append('}'); + return sb.toString(); + } +} \ No newline at end of file diff --git a/opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryStorageAdapter.java b/opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryStorageAdapter.java new file mode 100644 index 0000000000..ab6fb1577c --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/directory/xml/XmlDirectoryStorageAdapter.java @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ + +package org.opendaylight.controller.config.persist.storage.directory.xml; + +import com.google.common.base.Preconditions; +import org.opendaylight.controller.config.persist.api.Persister; +import org.opendaylight.controller.config.persist.api.PropertiesProvider; +import org.opendaylight.controller.config.persist.api.StorageAdapter; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.io.File; + +/** + * StorageAdapter that retrieves initial configuration from a directory. If multiple files are present, snapshot and + * required capabilities will be merged together. Writing to this persister is not supported. + */ +public class XmlDirectoryStorageAdapter implements StorageAdapter { + private static final Logger logger = LoggerFactory.getLogger(XmlDirectoryStorageAdapter.class); + + public static final String DIRECTORY_STORAGE_PROP = "directoryStorage"; + + + @Override + public Persister instantiate(PropertiesProvider propertiesProvider) { + String fileStorageProperty = propertiesProvider.getProperty(DIRECTORY_STORAGE_PROP); + Preconditions.checkNotNull(fileStorageProperty, "Unable to find " + propertiesProvider.getFullKeyForReporting(DIRECTORY_STORAGE_PROP)); + File storage = new File(fileStorageProperty); + logger.debug("Using {}", storage); + return new XmlDirectoryPersister(storage); + } + +} diff --git a/opendaylight/config/config-persister-directory-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/directory/xml/DirectoryStorageAdapterTest.java b/opendaylight/config/config-persister-directory-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/directory/xml/DirectoryStorageAdapterTest.java new file mode 100644 index 0000000000..73061f81de --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/directory/xml/DirectoryStorageAdapterTest.java @@ -0,0 +1,88 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ + +package org.opendaylight.controller.config.persist.storage.directory.xml; + +import org.junit.Test; +import org.opendaylight.controller.config.persist.api.ConfigSnapshotHolder; + +import java.io.File; +import java.util.Collections; +import java.util.List; +import java.util.SortedSet; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; +import static org.junit.Assert.fail; + +public class DirectoryStorageAdapterTest { + XmlDirectoryPersister tested; + + @Test + public void testEmptyDirectory() throws Exception { + File folder = new File("target/emptyFolder"); + folder.mkdir(); + tested = new XmlDirectoryPersister((folder)); + assertEquals(Collections.emptyList(), tested.loadLastConfigs()); + + try { + tested.persistConfig(new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + throw new RuntimeException(); + } + + @Override + public SortedSet getCapabilities() { + throw new RuntimeException(); + } + }); + fail(); + } catch (UnsupportedOperationException e) { + + } + } + + private File getFolder(String folderName) { + File result = new File(("src/test/resources/" + + folderName).replace("/", File.separator)); + assertTrue(result + " is not a directory", result.isDirectory()); + return result; + } + + @Test + public void testOneFile() throws Exception { + File folder = getFolder("oneFile"); + tested = new XmlDirectoryPersister((folder)); + List results = tested.loadLastConfigs(); + assertEquals(1, results.size()); + ConfigSnapshotHolder result = results.get(0); + assertResult(result, "1", "cap1&rev", "cap2", "capa a"); + } + + private void assertResult(ConfigSnapshotHolder result, String s, String... caps) { + assertEquals(s, result.getConfigSnapshot().replaceAll("\\s", "")); + int i = 0; + for (String capFromSnapshot : result.getCapabilities()) { + assertEquals(capFromSnapshot, caps[i++]); + } + } + + @Test + public void testTwoFiles() throws Exception { + File folder = getFolder("twoFiles"); + tested = new XmlDirectoryPersister((folder)); + List results = tested.loadLastConfigs(); + assertEquals(2, results.size()); + + assertResult(results.get(0), "1", "cap1-a", "cap2-a", "capa a-a"); + assertResult(results.get(1), "2", "cap1-b", "cap2-b", "capa a-b"); + + } + +} diff --git a/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/oneFile/controller.config.xml b/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/oneFile/controller.config.xml new file mode 100644 index 0000000000..aa8b14c9c4 --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/oneFile/controller.config.xml @@ -0,0 +1,10 @@ + + + cap1&rev + cap2 + capa a + + + 1 + + \ No newline at end of file diff --git a/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config1.xml b/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config1.xml new file mode 100644 index 0000000000..28f112e4fa --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config1.xml @@ -0,0 +1,10 @@ + + + cap1-a + cap2-a + capa a-a + + + 1 + + \ No newline at end of file diff --git a/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config2.xml b/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config2.xml new file mode 100644 index 0000000000..8fed29d182 --- /dev/null +++ b/opendaylight/config/config-persister-directory-xml-adapter/src/test/resources/twoFiles/controller.config2.xml @@ -0,0 +1,10 @@ + + + cap1-b + cap2-b + capa a-b + + + 2 + + \ No newline at end of file diff --git a/opendaylight/config/config-persister-file-xml-adapter/pom.xml b/opendaylight/config/config-persister-file-xml-adapter/pom.xml new file mode 100644 index 0000000000..abbec382b7 --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/pom.xml @@ -0,0 +1,87 @@ + + + 4.0.0 + + config-subsystem + org.opendaylight.controller + 0.2.3-SNAPSHOT + .. + + config-persister-file-xml-adapter + ${project.artifactId} + bundle + + + + + ${project.groupId} + config-persister-api + + + org.apache.commons + commons-lang3 + + + com.google.guava + guava + + + org.slf4j + slf4j-api + + + + org.eclipse.persistence + org.eclipse.persistence.moxy + + + org.eclipse.persistence + org.eclipse.persistence.core + + + + + org.opendaylight.bgpcep + mockito-configuration + test + + + + + + + + org.codehaus.groovy.maven + gmaven-plugin + + + generate-sources + + execute + + + + System.setProperty("osgiversion", "${project.version}".replace('-', '.')) + + + + + + + org.apache.felix + maven-bundle-plugin + + + ${project.groupId}.config-persister-impl;bundle-version=${osgiversion} + + org.opendaylight.controller.config.persister.storage.adapter + + + + + + + + diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/XmlFileStorageAdapter.java b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/XmlFileStorageAdapter.java new file mode 100644 index 0000000000..e75c62b81d --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/XmlFileStorageAdapter.java @@ -0,0 +1,149 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ + +package org.opendaylight.controller.config.persist.storage.file.xml; + +import com.google.common.annotations.VisibleForTesting; +import com.google.common.base.Optional; +import com.google.common.base.Preconditions; +import com.google.common.collect.Lists; +import org.opendaylight.controller.config.persist.api.ConfigSnapshotHolder; +import org.opendaylight.controller.config.persist.api.Persister; +import org.opendaylight.controller.config.persist.api.PropertiesProvider; +import org.opendaylight.controller.config.persist.api.StorageAdapter; +import org.opendaylight.controller.config.persist.storage.file.xml.model.Config; +import org.opendaylight.controller.config.persist.storage.file.xml.model.ConfigSnapshot; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.io.File; +import java.io.IOException; +import java.util.Collections; +import java.util.List; +import java.util.SortedSet; + +/** + * StorageAdapter that stores configuration in an xml file. + */ +public class XmlFileStorageAdapter implements StorageAdapter, Persister { + private static final Logger logger = LoggerFactory.getLogger(XmlFileStorageAdapter.class); + + public static final String FILE_STORAGE_PROP = "fileStorage"; + public static final String NUMBER_OF_BACKUPS = "numberOfBackups"; + + private static Integer numberOfStoredBackups; + private File storage; + + @Override + public Persister instantiate(PropertiesProvider propertiesProvider) { + File storage = extractStorageFileFromProperties(propertiesProvider); + logger.debug("Using file {}", storage.getAbsolutePath()); + // Create file if it does not exist + File parentFile = storage.getAbsoluteFile().getParentFile(); + if (parentFile.exists() == false) { + logger.debug("Creating parent folders {}", parentFile); + parentFile.mkdirs(); + } + if (storage.exists() == false) { + logger.debug("Storage file does not exist, creating empty file"); + try { + boolean result = storage.createNewFile(); + if (result == false) + throw new RuntimeException("Unable to create storage file " + storage); + } catch (IOException e) { + throw new RuntimeException("Unable to create storage file " + storage, e); + } + } + if (numberOfStoredBackups == 0) { + throw new RuntimeException(NUMBER_OF_BACKUPS + + " property should be either set to positive value, or ommited. Can not be set to 0."); + } + setFileStorage(storage); + return this; + } + + @VisibleForTesting + public void setFileStorage(File storage) { + this.storage = storage; + } + + @VisibleForTesting + public void setNumberOfBackups(Integer numberOfBackups) { + numberOfStoredBackups = numberOfBackups; + } + + private static File extractStorageFileFromProperties(PropertiesProvider propertiesProvider) { + String fileStorageProperty = propertiesProvider.getProperty(FILE_STORAGE_PROP); + Preconditions.checkNotNull(fileStorageProperty, "Unable to find " + propertiesProvider.getFullKeyForReporting(FILE_STORAGE_PROP)); + File result = new File(fileStorageProperty); + String numberOfBackupsAsString = propertiesProvider.getProperty(NUMBER_OF_BACKUPS); + if (numberOfBackupsAsString != null) { + numberOfStoredBackups = Integer.valueOf(numberOfBackupsAsString); + } else { + numberOfStoredBackups = Integer.MAX_VALUE; + } + logger.trace("Property {} set to {}", NUMBER_OF_BACKUPS, numberOfStoredBackups); + return result; + } + + @Override + public void persistConfig(ConfigSnapshotHolder holder) throws IOException { + Preconditions.checkNotNull(storage, "Storage file is null"); + + Config cfg = Config.fromXml(storage); + cfg.addConfigSnapshot(ConfigSnapshot.fromConfigSnapshot(holder), numberOfStoredBackups); + cfg.toXml(storage); + } + + @Override + public List loadLastConfigs() throws IOException { + Preconditions.checkNotNull(storage, "Storage file is null"); + + if (!storage.exists()) { + return Collections.emptyList(); + } + + Optional lastSnapshot = Config.fromXml(storage).getLastSnapshot(); + + if (lastSnapshot.isPresent()) + return Lists.newArrayList(toConfigSnapshot(lastSnapshot.get())); + else + return Collections.emptyList(); + } + + + public ConfigSnapshotHolder toConfigSnapshot(final ConfigSnapshot configSnapshot) { + return new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + return configSnapshot.getConfigSnapshot(); + } + + @Override + public SortedSet getCapabilities() { + return configSnapshot.getCapabilities(); + } + + @Override + public String toString() { + return configSnapshot.toString(); + } + }; + } + + @Override + public void close() { + + } + + @Override + public String toString() { + return "XmlFileStorageAdapter [storage=" + storage + "]"; + } + +} diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/CapabilityHandler.java b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/CapabilityHandler.java new file mode 100644 index 0000000000..d384df6989 --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/CapabilityHandler.java @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.config.persist.storage.file.xml.model; + +import javax.xml.bind.ValidationEventHandler; +import javax.xml.bind.annotation.DomHandler; +import javax.xml.transform.Source; +import javax.xml.transform.stream.StreamResult; +import javax.xml.transform.stream.StreamSource; +import java.io.StringReader; +import java.io.StringWriter; + +class CapabilityHandler implements DomHandler { + + private static final String START_TAG = ""; + private static final String END_TAG = ""; + + private StringWriter xmlWriter = new StringWriter(); + + public StreamResult createUnmarshaller(ValidationEventHandler errorHandler) { + xmlWriter.getBuffer().setLength(0); + return new StreamResult(xmlWriter); + } + + public String getElement(StreamResult rt) { + String xml = rt.getWriter().toString(); + int beginIndex = xml.indexOf(START_TAG) + START_TAG.length(); + int endIndex = xml.indexOf(END_TAG); + return xml.substring(beginIndex, endIndex); + } + + public Source marshal(String n, ValidationEventHandler errorHandler) { + try { + String xml = START_TAG + n.trim() + END_TAG; + StringReader xmlReader = new StringReader(xml); + return new StreamSource(xmlReader); + } catch(Exception e) { + throw new RuntimeException(e); + } + } + +} diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/Config.java b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/Config.java new file mode 100644 index 0000000000..fb84651ca1 --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/Config.java @@ -0,0 +1,109 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.config.persist.storage.file.xml.model; + +import com.google.common.base.Charsets; +import com.google.common.base.Optional; +import com.google.common.collect.Iterables; +import com.google.common.collect.Lists; +import com.google.common.io.Files; +import org.apache.commons.lang3.StringUtils; + +import javax.xml.bind.JAXBContext; +import javax.xml.bind.JAXBException; +import javax.xml.bind.Marshaller; +import javax.xml.bind.Unmarshaller; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlElementWrapper; +import javax.xml.bind.annotation.XmlRootElement; +import java.io.File; +import java.io.IOException; +import java.util.List; + +@XmlRootElement(name = "persisted-snapshots") +public final class Config { + + private List snapshots; + + Config(List snapshots) { + this.snapshots = snapshots; + } + + public Config() { + this.snapshots = Lists.newArrayList(); + } + + @XmlElement(name = "snapshot") + @XmlElementWrapper(name = "snapshots") + public List getSnapshots() { + return snapshots; + } + + public void setSnapshots(List snapshots) { + this.snapshots = snapshots; + } + + public void toXml(File to) { + try { + + // TODO Moxy has to be used instead of default jaxb impl due to a bug + // default implementation has a bug that prevents from serializing xml in a string + JAXBContext jaxbContext = org.eclipse.persistence.jaxb.JAXBContextFactory.createContext(new Class[]{Config.class}, null); + + Marshaller marshaller = jaxbContext.createMarshaller(); + + marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); + + marshaller.marshal(this, to); + } catch (JAXBException e) { + throw new PersistException("Unable to persist configuration", e); + } + } + + public static Config fromXml(File from) { + if(isEmpty(from)) + return new Config(); + + try { + JAXBContext jaxbContext = JAXBContext.newInstance(Config.class); + Unmarshaller um = jaxbContext.createUnmarshaller(); + + return (Config) um.unmarshal(from); + } catch (JAXBException e) { + throw new PersistException("Unable to restore configuration", e); + } + } + + private static boolean isEmpty(File from) { + return from.length() == 0 || isBlank(from); + } + + private static boolean isBlank(File from) { + try { + return StringUtils.isBlank(Files.toString(from, Charsets.UTF_8)); + } catch (IOException e) { + throw new IllegalStateException("Unexpected error reading file" + from, e); + } + } + + public Optional getLastSnapshot() { + ConfigSnapshot last = Iterables.getLast(snapshots, null); + return last == null ? Optional.absent() : Optional.of(last); + } + + public void addConfigSnapshot(ConfigSnapshot snap, int numberOfStoredBackups) { + if(shouldReplaceLast(numberOfStoredBackups) && snapshots.isEmpty() == false) { + snapshots.remove(0); + } + snapshots.add(snap); + } + + private boolean shouldReplaceLast(int numberOfStoredBackups) { + return numberOfStoredBackups == snapshots.size(); + } +} diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/ConfigSnapshot.java b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/ConfigSnapshot.java new file mode 100644 index 0000000000..41976000ba --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/ConfigSnapshot.java @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.config.persist.storage.file.xml.model; + +import org.opendaylight.controller.config.persist.api.ConfigSnapshotHolder; + +import javax.xml.bind.annotation.XmlAnyElement; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlElementWrapper; +import javax.xml.bind.annotation.XmlRootElement; +import java.util.SortedSet; + +@XmlRootElement(name = "snapshot") +public class ConfigSnapshot { + + private String configSnapshot; + private SortedSet capabilities; + + ConfigSnapshot(String configXml, SortedSet capabilities) { + this.configSnapshot = configXml; + this.capabilities = capabilities; + } + + public ConfigSnapshot() { + } + + public static ConfigSnapshot fromConfigSnapshot(ConfigSnapshotHolder cfg) { + return new ConfigSnapshot(cfg.getConfigSnapshot(), cfg.getCapabilities()); + } + + @XmlAnyElement(SnapshotHandler.class) + public String getConfigSnapshot() { + return configSnapshot; + } + + public void setConfigSnapshot(String configSnapshot) { + this.configSnapshot = configSnapshot; + } + + @XmlElement(name = "capability") + @XmlElementWrapper(name = "required-capabilities") + public SortedSet getCapabilities() { + return capabilities; + } + + public void setCapabilities(SortedSet capabilities) { + this.capabilities = capabilities; + } + + @Override + public String toString() { + final StringBuffer sb = new StringBuffer("ConfigSnapshot{"); + sb.append("configSnapshot='").append(configSnapshot).append('\''); + sb.append(", capabilities=").append(capabilities); + sb.append('}'); + return sb.toString(); + } +} diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/PersistException.java b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/PersistException.java new file mode 100644 index 0000000000..29d623274c --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/PersistException.java @@ -0,0 +1,15 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.config.persist.storage.file.xml.model; + +final class PersistException extends RuntimeException { + + public PersistException(String s, Exception e) { + super(s, e); + } +} diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/SnapshotHandler.java b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/SnapshotHandler.java new file mode 100644 index 0000000000..dd39410409 --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/main/java/org/opendaylight/controller/config/persist/storage/file/xml/model/SnapshotHandler.java @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.config.persist.storage.file.xml.model; + +import javax.xml.bind.ValidationEventHandler; +import javax.xml.bind.annotation.DomHandler; +import javax.xml.transform.Source; +import javax.xml.transform.stream.StreamResult; +import javax.xml.transform.stream.StreamSource; +import java.io.StringReader; +import java.io.StringWriter; + +class SnapshotHandler implements DomHandler { + + private static final String START_TAG = ""; + private static final String END_TAG = ""; + + private StringWriter xmlWriter = new StringWriter(); + + public StreamResult createUnmarshaller(ValidationEventHandler errorHandler) { + xmlWriter.getBuffer().setLength(0); + return new StreamResult(xmlWriter); + } + + public String getElement(StreamResult rt) { + String xml = rt.getWriter().toString(); + int beginIndex = xml.indexOf(START_TAG) + START_TAG.length(); + int endIndex = xml.indexOf(END_TAG); + return xml.substring(beginIndex, endIndex); + } + + public Source marshal(String n, ValidationEventHandler errorHandler) { + try { + String xml = START_TAG + n.trim() + END_TAG; + StringReader xmlReader = new StringReader(xml); + return new StreamSource(xmlReader); + } catch(Exception e) { + throw new RuntimeException(e); + } + } + +} diff --git a/opendaylight/config/config-persister-file-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/file/xml/FileStorageAdapterTest.java b/opendaylight/config/config-persister-file-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/file/xml/FileStorageAdapterTest.java new file mode 100644 index 0000000000..d6bbeb31da --- /dev/null +++ b/opendaylight/config/config-persister-file-xml-adapter/src/test/java/org/opendaylight/controller/config/persist/storage/file/xml/FileStorageAdapterTest.java @@ -0,0 +1,188 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ + +package org.opendaylight.controller.config.persist.storage.file.xml; + +import com.google.common.base.Charsets; +import junit.framework.Assert; +import org.junit.Before; +import org.junit.Test; +import org.mockito.Mockito; +import org.opendaylight.controller.config.persist.api.ConfigSnapshotHolder; + +import java.io.File; +import java.nio.file.Files; +import java.util.List; +import java.util.SortedSet; +import java.util.TreeSet; + +import static junit.framework.Assert.assertFalse; +import static org.hamcrest.CoreMatchers.is; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertThat; + +public class FileStorageAdapterTest { + + private static int i; + private File file; + + @Before + public void setUp() throws Exception { + file = Files.createTempFile("testFilePersist", ".txt").toFile(); + if (!file.exists()) + return; + com.google.common.io.Files.write("", file, Charsets.UTF_8); + i = 1; + } + + @Test + public void testFileAdapter() throws Exception { + XmlFileStorageAdapter storage = new XmlFileStorageAdapter(); + storage.setFileStorage(file); + storage.setNumberOfBackups(Integer.MAX_VALUE); + final ConfigSnapshotHolder holder = new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + return createConfig(); + } + + @Override + public SortedSet getCapabilities() { + return createCaps(); + } + }; + storage.persistConfig(holder); + + storage.persistConfig(holder); + + assertEquals(27, com.google.common.io.Files.readLines(file, Charsets.UTF_8).size()); + List lastConf = storage.loadLastConfigs(); + assertEquals(1, lastConf.size()); + ConfigSnapshotHolder configSnapshotHolder = lastConf.get(0); + assertEquals("2", + configSnapshotHolder.getConfigSnapshot().replaceAll("\\s", "")); + assertEquals(createCaps(), configSnapshotHolder.getCapabilities()); + + storage = new XmlFileStorageAdapter(); + storage.setFileStorage(file); + storage.setNumberOfBackups(Integer.MAX_VALUE); + + List last = storage.loadLastConfigs(); + Assert.assertEquals(createCaps(), last.get(0).getCapabilities()); + } + + private SortedSet createCaps() { + SortedSet caps = new TreeSet<>(); + + caps.add("cap1" + i); + caps.add("cap2" + i); + caps.add("urn:opendaylight:params:xml:ns:yang:controller:netty?module=netty&revision=2013-11-19" + i); + caps.add("capaaaa as dasfasdf s2" + i); + return caps; + } + + @Test + public void testFileAdapterOneBackup() throws Exception { + XmlFileStorageAdapter storage = new XmlFileStorageAdapter(); + storage.setFileStorage(file); + storage.setNumberOfBackups(1); + final ConfigSnapshotHolder holder = new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + return createConfig(); + } + + @Override + public SortedSet getCapabilities() { + return createCaps(); + } + }; + storage.persistConfig(holder); + + storage.persistConfig(holder); + + assertEquals(16, com.google.common.io.Files.readLines(file, Charsets.UTF_8).size()); + + List lastConf = storage.loadLastConfigs(); + assertEquals(1, lastConf.size()); + ConfigSnapshotHolder configSnapshotHolder = lastConf.get(0); + assertEquals("2", + configSnapshotHolder.getConfigSnapshot().replaceAll("\\s", "")); + } + + @Test + public void testFileAdapterOnlyTwoBackups() throws Exception { + XmlFileStorageAdapter storage = new XmlFileStorageAdapter(); + storage.setFileStorage(file); + storage.setNumberOfBackups(2); + final ConfigSnapshotHolder holder = new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + return createConfig(); + } + + @Override + public SortedSet getCapabilities() { + return createCaps(); + } + }; + storage.persistConfig(holder); + + storage.persistConfig(holder); + storage.persistConfig(holder); + + List readLines = com.google.common.io.Files.readLines(file, Charsets.UTF_8); + assertEquals(27, readLines.size()); + + List lastConf = storage.loadLastConfigs(); + assertEquals(1, lastConf.size()); + ConfigSnapshotHolder configSnapshotHolder = lastConf.get(0); + assertEquals("3", + configSnapshotHolder.getConfigSnapshot().replaceAll("\\s", "")); + assertFalse(readLines.contains(holder.getConfigSnapshot())); + } + + @Test + public void testNoLastConfig() throws Exception { + File file = Files.createTempFile("testFilePersist", ".txt").toFile(); + if (!file.exists()) + return; + XmlFileStorageAdapter storage = new XmlFileStorageAdapter(); + storage.setFileStorage(file); + + List elementOptional = storage.loadLastConfigs(); + assertThat(elementOptional.size(), is(0)); + } + + @Test(expected = NullPointerException.class) + public void testNoProperties() throws Exception { + XmlFileStorageAdapter storage = new XmlFileStorageAdapter(); + storage.loadLastConfigs(); + } + + @Test(expected = NullPointerException.class) + public void testNoProperties2() throws Exception { + XmlFileStorageAdapter storage = new XmlFileStorageAdapter(); + storage.persistConfig(new ConfigSnapshotHolder() { + @Override + public String getConfigSnapshot() { + return Mockito.mock(String.class); + } + + @Override + public SortedSet getCapabilities() { + return new TreeSet<>(); + } + } ); + } + + static String createConfig() { + return "" + i++ + ""; + } + +} diff --git a/opendaylight/config/pom.xml b/opendaylight/config/pom.xml index 9f0145fffe..eba5e07c0f 100644 --- a/opendaylight/config/pom.xml +++ b/opendaylight/config/pom.xml @@ -26,6 +26,7 @@ config-util config-persister-api config-persister-file-adapter + config-persister-file-xml-adapter yang-jmx-generator yang-jmx-generator-plugin yang-store-api @@ -39,6 +40,7 @@ netty-event-executor-config netty-timer-config config-persister-directory-adapter + config-persister-directory-xml-adapter yang-test-plugin diff --git a/opendaylight/distribution/opendaylight/pom.xml b/opendaylight/distribution/opendaylight/pom.xml index 033d0573f9..b7a4638c60 100644 --- a/opendaylight/distribution/opendaylight/pom.xml +++ b/opendaylight/distribution/opendaylight/pom.xml @@ -223,11 +223,21 @@ config-persister-file-adapter ${config.version} - - org.opendaylight.controller - config-persister-directory-adapter - ${config.version} - + + org.opendaylight.controller + config-persister-file-xml-adapter + ${config.version} + + + org.opendaylight.controller + config-persister-directory-adapter + ${config.version} + + + org.opendaylight.controller + config-persister-directory-xml-adapter + ${config.version} + diff --git a/opendaylight/distribution/opendaylight/src/main/resources/configuration/config.ini b/opendaylight/distribution/opendaylight/src/main/resources/configuration/config.ini index 7d57e6005e..ba5d862c57 100644 --- a/opendaylight/distribution/opendaylight/src/main/resources/configuration/config.ini +++ b/opendaylight/distribution/opendaylight/src/main/resources/configuration/config.ini @@ -29,8 +29,16 @@ netconf.config.persister.1.storageAdapterClass=org.opendaylight.controller.confi netconf.config.persister.1.properties.directoryStorage=configuration/initial/ netconf.config.persister.1.readonly=true -netconf.config.persister.2.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.FileStorageAdapter -netconf.config.persister.2.properties.fileStorage=configuration/current/controller.currentconfig.txt +#netconf.config.persister.3.storageAdapterClass=org.opendaylight.controller.config.persist.storage.directory.xml.XmlDirectoryStorageAdapter +#netconf.config.persister.3.properties.directoryStorage=configuration/initialXml/ +#netconf.config.persister.3.readonly=true + +#netconf.config.persister.4.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.FileStorageAdapter +#netconf.config.persister.4.properties.fileStorage=configuration/current/controller.currentconfig.txt +#netconf.config.persister.4.properties.numberOfBackups=1 + +netconf.config.persister.2.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.xml.XmlFileStorageAdapter +netconf.config.persister.2.properties.fileStorage=configuration/current/controller.currentconfig.xml netconf.config.persister.2.properties.numberOfBackups=1 diff --git a/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/attributes/AttributesConstants.java b/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/attributes/AttributesConstants.java index 4f9e1fe087..23cdabf69f 100644 --- a/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/attributes/AttributesConstants.java +++ b/opendaylight/netconf/config-netconf-connector/src/main/java/org/opendaylight/controller/netconf/confignetconfconnector/mapping/attributes/AttributesConstants.java @@ -1,10 +1,9 @@ -/** - * @author Maros Marsalek +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. * - * 12 2013 - * - * Copyright (c) 2012 by Cisco Systems, Inc. - * All rights reserved. + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html */ package org.opendaylight.controller.netconf.confignetconfconnector.mapping.attributes; 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 a4f5e4999c..77f3cf283f 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 @@ -97,7 +97,11 @@ public final class Services { Preconditions.checkArgument(refNameToInstance != null, "No serviceInstances mapped to " + serviceName + " , " + serviceNameToRefNameToInstance.keySet()); - ServiceInstance serviceInstance = ServiceInstance.fromString(refNameToInstance.get(refName)); + String instanceId = refNameToInstance.get(refName); + Preconditions.checkArgument(instanceId != null, "No serviceInstances mapped to " + serviceName + ":" + + refName + ", " + serviceNameToRefNameToInstance.keySet()); + + ServiceInstance serviceInstance = ServiceInstance.fromString(instanceId); Preconditions.checkArgument(serviceInstance != null, "No serviceInstance mapped to " + refName + " under service name " + serviceName + " , " + refNameToInstance.keySet()); return serviceInstance; diff --git a/opendaylight/netconf/config-netconf-connector/src/test/java/org/opendaylight/controller/netconf/confignetconfconnector/NetconfMappingTest.java b/opendaylight/netconf/config-netconf-connector/src/test/java/org/opendaylight/controller/netconf/confignetconfconnector/NetconfMappingTest.java index ccb793149c..b248342a0a 100644 --- a/opendaylight/netconf/config-netconf-connector/src/test/java/org/opendaylight/controller/netconf/confignetconfconnector/NetconfMappingTest.java +++ b/opendaylight/netconf/config-netconf-connector/src/test/java/org/opendaylight/controller/netconf/confignetconfconnector/NetconfMappingTest.java @@ -12,6 +12,7 @@ import com.google.common.base.Optional; import com.google.common.base.Preconditions; import com.google.common.collect.Lists; import com.google.common.collect.Maps; +import com.google.common.collect.Sets; import org.apache.commons.lang3.StringUtils; import org.junit.Before; import org.junit.Ignore; @@ -75,9 +76,11 @@ import java.util.Arrays; import java.util.Collection; import java.util.List; import java.util.Map; +import java.util.Set; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertThat; +import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import static org.mockito.Mockito.doNothing; import static org.mockito.Mockito.doReturn; @@ -497,17 +500,20 @@ public class NetconfMappingTest extends AbstractConfigTest { XmlElement modulesElement = XmlElement.fromDomElement(response).getOnlyChildElement("data") .getOnlyChildElement("modules"); - XmlElement configAttributeType = null; + List expectedValues = Lists.newArrayList("default-string", "configAttributeType"); + Set configAttributeType = Sets.newHashSet(); + for (XmlElement moduleElement : modulesElement.getChildElements("module")) { for (XmlElement type : moduleElement.getChildElements("type")) { if (type.getAttribute(XmlUtil.XMLNS_ATTRIBUTE_KEY).equals("") == false) { - configAttributeType = type; + configAttributeType.add(type.getTextContent()); } } } - // TODO verify if should be default value - assertEquals("default-string", configAttributeType.getTextContent()); + for (String expectedValue : expectedValues) { + assertTrue(configAttributeType.contains(expectedValue)); + } } private Map> getMbes() throws Exception { diff --git a/opendaylight/netconf/config-persister-impl/pom.xml b/opendaylight/netconf/config-persister-impl/pom.xml index c6caf417a1..7fc2b584b8 100644 --- a/opendaylight/netconf/config-persister-impl/pom.xml +++ b/opendaylight/netconf/config-persister-impl/pom.xml @@ -43,7 +43,9 @@ org.opendaylight.controller - config-persister-file-adapter + config-persister-file-xml-adapter + test + ${config.version} @@ -60,8 +62,8 @@ org.opendaylight.controller - config-persister-directory-adapter - ${parent.version} + config-persister-directory-xml-adapter + ${config.version} test diff --git a/opendaylight/netconf/config-persister-impl/src/main/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregator.java b/opendaylight/netconf/config-persister-impl/src/main/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregator.java index 7e9dce67bd..f168bb3634 100644 --- a/opendaylight/netconf/config-persister-impl/src/main/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregator.java +++ b/opendaylight/netconf/config-persister-impl/src/main/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregator.java @@ -34,7 +34,7 @@ import java.util.ListIterator; * Example configuration:
  netconf.config.persister.active=2,3
  # read startup configuration
- netconf.config.persister.1.storageAdapterClass=org.opendaylight.controller.config.persist.storage.directory.DirectoryStorageAdapter
+ netconf.config.persister.1.storageAdapterClass=org.opendaylight.controller.config.persist.storage.directory.xml.XmlDirectoryStorageAdapter
  netconf.config.persister.1.properties.fileStorage=configuration/initial/
 
  netconf.config.persister.2.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.FileStorageAdapter
diff --git a/opendaylight/netconf/config-persister-impl/src/test/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregatorTest.java b/opendaylight/netconf/config-persister-impl/src/test/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregatorTest.java
index 227018bf5b..acea75a743 100644
--- a/opendaylight/netconf/config-persister-impl/src/test/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregatorTest.java
+++ b/opendaylight/netconf/config-persister-impl/src/test/java/org/opendaylight/controller/netconf/persist/impl/PersisterAggregatorTest.java
@@ -11,7 +11,7 @@ package org.opendaylight.controller.netconf.persist.impl;
 import org.junit.Test;
 import org.opendaylight.controller.config.persist.api.ConfigSnapshotHolder;
 import org.opendaylight.controller.config.persist.api.Persister;
-import org.opendaylight.controller.config.persist.storage.file.FileStorageAdapter;
+import org.opendaylight.controller.config.persist.storage.file.xml.XmlFileStorageAdapter;
 import org.opendaylight.controller.netconf.persist.impl.osgi.ConfigPersisterActivator;
 import org.opendaylight.controller.netconf.persist.impl.osgi.PropertiesProviderBaseImpl;
 
@@ -93,7 +93,7 @@ public class PersisterAggregatorTest {
         List persisters = persisterAggregator.getPersisterWithConfigurations();
         assertEquals(1, persisters.size());
         PersisterWithConfiguration persister = persisters.get(0);
-        assertEquals(FileStorageAdapter.class.getName() ,persister.getStorage().getClass().getName());
+        assertEquals(XmlFileStorageAdapter.class.getName() ,persister.getStorage().getClass().getName());
         assertFalse(persister.isReadOnly());
     }
 
diff --git a/opendaylight/netconf/config-persister-impl/src/test/resources/test2.properties b/opendaylight/netconf/config-persister-impl/src/test/resources/test2.properties
index 222e7cef47..729c67d6c5 100644
--- a/opendaylight/netconf/config-persister-impl/src/test/resources/test2.properties
+++ b/opendaylight/netconf/config-persister-impl/src/test/resources/test2.properties
@@ -1,9 +1,9 @@
 netconf.config.persister.active=2
 # read startup configuration
-netconf.config.persister.1.storageAdapterClass=org.opendaylight.controller.config.persist.storage.directory.DirectoryStorageAdapter
+netconf.config.persister.1.storageAdapterClass=org.opendaylight.controller.config.persist.storage.directory.xml.XmlDirectoryStorageAdapter
 netconf.config.persister.1.properties.directoryStorage=target/configuration/initial/
 netconf.config.persister.1.readonly=true
 
-netconf.config.persister.2.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.FileStorageAdapter
+netconf.config.persister.2.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.xml.XmlFileStorageAdapter
 netconf.config.persister.2.properties.fileStorage=target/configuration/current/controller.config.2.txt
 netconf.config.persister.2.properties.numberOfBackups=3
diff --git a/opendaylight/netconf/config-persister-impl/src/test/resources/test3.properties b/opendaylight/netconf/config-persister-impl/src/test/resources/test3.properties
index a1645ad8c4..90ba77273b 100644
--- a/opendaylight/netconf/config-persister-impl/src/test/resources/test3.properties
+++ b/opendaylight/netconf/config-persister-impl/src/test/resources/test3.properties
@@ -1,4 +1,4 @@
 netconf.config.persister.active=3
-netconf.config.persister.3.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.FileStorageAdapter
+netconf.config.persister.3.storageAdapterClass=org.opendaylight.controller.config.persist.storage.file.xml.XmlFileStorageAdapter
 netconf.config.persister.3.properties.fileStorage=target/configuration/current/controller.config.2.txt
 netconf.config.persister.3.properties.numberOfBackups=0
-- 
2.36.6