import com.google.common.base.Optional;
import com.google.common.base.Preconditions;
import com.google.common.collect.Lists;
+import java.io.File;
+import java.io.IOException;
+import java.util.Collections;
+import java.util.List;
+import java.util.Set;
+import java.util.SortedSet;
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.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);
+ private static final Logger LOG = 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;
+ private static volatile XmlFileStorageAdapter instance;
+ private volatile ConfigSnapshot lastCfgSnapshotCache;
+ private volatile Optional<FeatureListProvider> featuresService = Optional.absent();
+
+ @VisibleForTesting
+ public void reset() {
+ instance = null;
+ lastCfgSnapshotCache = null;
+ featuresService = null;
+ }
+
@Override
public Persister instantiate(PropertiesProvider propertiesProvider) {
+ if(instance != null) {
+ return instance;
+ }
+
File storage = extractStorageFileFromProperties(propertiesProvider);
- LOGGER.debug("Using file {}", storage.getAbsolutePath());
+ LOG.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);
+ LOG.debug("Creating parent folders {}", parentFile);
parentFile.mkdirs();
}
if (storage.exists() == false) {
- LOGGER.debug("Storage file does not exist, creating empty file");
+ LOG.debug("Storage file does not exist, creating empty file");
try {
boolean result = storage.createNewFile();
- if (result == false)
+ 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);
}
+ " property should be either set to positive value, or ommited. Can not be set to 0.");
}
setFileStorage(storage);
+
+ instance = this;
return this;
}
+ public static Optional<XmlFileStorageAdapter> getInstance() {
+ return Optional.fromNullable(instance);
+ }
+
+ public Set<String> getPersistedFeatures() {
+ return lastCfgSnapshotCache == null ? Collections.<String>emptySet() : lastCfgSnapshotCache.getFeatures();
+ }
+
+ public void setFeaturesService(final FeatureListProvider featuresService) {
+ this.featuresService = Optional.of(featuresService);
+ }
+
@VisibleForTesting
public void setFileStorage(File storage) {
this.storage = storage;
} else {
numberOfStoredBackups = Integer.MAX_VALUE;
}
- LOGGER.trace("Property {} set to {}", NUMBER_OF_BACKUPS, numberOfStoredBackups);
+ LOG.trace("Property {} set to {}", NUMBER_OF_BACKUPS, numberOfStoredBackups);
return result;
}
public void persistConfig(ConfigSnapshotHolder holder) throws IOException {
Preconditions.checkNotNull(storage, "Storage file is null");
+ Set<String> installedFeatureIds = Collections.emptySet();
+ if(featuresService.isPresent()) {
+ installedFeatureIds = featuresService.get().listFeatures();
+ }
+
Config cfg = Config.fromXml(storage);
- cfg.addConfigSnapshot(ConfigSnapshot.fromConfigSnapshot(holder), numberOfStoredBackups);
+ cfg.addConfigSnapshot(ConfigSnapshot.fromConfigSnapshot(holder, installedFeatureIds), numberOfStoredBackups);
cfg.toXml(storage);
}
Optional<ConfigSnapshot> lastSnapshot = Config.fromXml(storage).getLastSnapshot();
if (lastSnapshot.isPresent()) {
- return Lists.newArrayList(toConfigSnapshot(lastSnapshot.get()));
+ lastCfgSnapshotCache = lastSnapshot.get();
+ return Lists.newArrayList(toConfigSnapshot(lastCfgSnapshotCache));
} else {
return Collections.emptyList();
}