blob: 15ee71c9bd1c8214f785af1af26b8fb42d850980 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.tamaya.spisupport;
import org.apache.tamaya.Configuration;
import org.apache.tamaya.ConfigurationSnapshot;
import org.apache.tamaya.TypeLiteral;
import org.apache.tamaya.spi.ConfigurationContext;
import org.apache.tamaya.spi.PropertyConverter;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.util.*;
import java.util.stream.Collectors;
/**
* /**
* Configuration implementation that stores all current values of a given (possibly dynamic, contextual and non server
* capable instance) and is fully serializable. Note that hereby only the scannable key/createValue pairs are considered.
*/
public class DefaultConfigurationSnapshot implements ConfigurationSnapshot, Serializable {
private static final long serialVersionUID = 1L;
/**
* The properties frozen.
*/
private DefaultConfiguration snapshot;
private long frozenAt = System.nanoTime();
private UUID id = UUID.randomUUID();
private DefaultConfigurationContext context;
private Set<String> keys = new HashSet<>();
/**
* Constructor.
*
* @param config The base configuration.
* @param keys The keys to evaluate, not null.
*/
public DefaultConfigurationSnapshot(Configuration config, Iterable<String> keys) {
for(String k:keys) {
this.keys.add(k);
}
ConfigurationContext ctx = config.getContext();
MetadataProvider metadataProvider = ctx.getServiceContext().getService(MetadataProvider.class,
DefaultMetaDataProvider::new);
context = new DefaultConfigurationContext(ctx.getServiceContext(),
ctx.getPropertyFilters(),
ctx.getPropertySources().stream()
.map(ps -> DefaultPropertySourceSnapshot.of(ps, this.keys)).collect(Collectors.toList()),
ctx.getPropertyConverters(),
metadataProvider);
this.snapshot = new DefaultConfiguration(context);
if(this.keys.isEmpty()){
this.keys.addAll(this.snapshot.getProperties().keySet());
}
this.keys = Collections.unmodifiableSet(this.keys);
}
/**
* Constructor.
*
* @param config The base configuration.
*/
public DefaultConfigurationSnapshot(Configuration config) {
ConfigurationContext ctx = config.getContext();
MetadataProvider metadataProvider = ctx.getServiceContext().getService(MetadataProvider.class,
DefaultMetaDataProvider::new);
context = new DefaultConfigurationContext(ctx.getServiceContext(),
ctx.getPropertyFilters(),
ctx.getPropertySources().stream()
.map(ps -> new DefaultPropertySourceSnapshot(ps)).collect(Collectors.toList()),
ctx.getPropertyConverters(),
metadataProvider);
this.snapshot = new DefaultConfiguration(context);
this.keys = Collections.unmodifiableSet(this.snapshot.getProperties().keySet());
}
@Override
public ConfigurationSnapshot getSnapshot(Iterable<String> keys) {
return new DefaultConfigurationSnapshot(this, keys);
}
/**
* Get the evaluated keys of this frozen coinfiguration.
* @return the keys, not null.
*/
@Override
public Set<String> getKeys() {
return keys;
}
@Override
public String get(String key) {
return this.snapshot.get(key);
}
@Override
public String getOrDefault(String key, String defaultValue) {
return this.snapshot.getOrDefault(key, defaultValue);
}
@Override
public <T> T getOrDefault(String key, Class<T> type, T defaultValue) {
return this.snapshot.getOrDefault(key, type, defaultValue);
}
@SuppressWarnings("unchecked")
@Override
public <T> T get(String key, Class<T> type) {
return snapshot.get(key, type);
}
/**
* Accesses the current String createValue for the given key and tries to convert it
* using the {@link PropertyConverter} instances provided by the current
* {@link ConfigurationContext}.
*
* @param key the property's absolute, or relative path, e.g. @code
* a/b/c/d.myProperty}.
* @param type The target type required, not null.
* @param <T> the createValue type
* @return the converted createValue, never null.
*/
@Override
public <T> T get(String key, TypeLiteral<T> type) {
return snapshot.get(key, type);
}
@Override
public <T> T getOrDefault(String key, TypeLiteral<T> type, T defaultValue) {
return snapshot.getOrDefault(key, type, defaultValue);
}
@Override
public Map<String, String> getProperties() {
return snapshot.getProperties();
}
@Override
public ConfigurationContext getContext() {
return snapshot.getContext();
}
/**
* <p>Returns the moment in time when this frozen configuration has been created.</p>
*
* <p>The time is taken from {@linkplain System#currentTimeMillis()}</p>
*
* @see System#currentTimeMillis()
* @return the moment in time when this configuration has been created
*/
@Override
public long getTimestamp() {
return frozenAt;
}
@Override
public boolean equals(Object o) {
if (this == o) {
return true;
}
if (o == null || getClass() != o.getClass()) {
return false;
}
DefaultConfigurationSnapshot that = (DefaultConfigurationSnapshot) o;
if (frozenAt != that.frozenAt) {
return false;
}
return Objects.equals(snapshot, that.snapshot);
}
@Override
public int hashCode() {
return Objects.hash(frozenAt, snapshot);
}
@Override
public String toString() {
return "FrozenConfiguration{" +
"id=" + getId() + "," +
"frozenAt=" + frozenAt + "," +
"config=" + snapshot +
'}';
}
/**
* <p>Returns the unique id of this frozen configuration.</p>
*
* @return the unique id of this frozen configuration, never {@code null}
*/
public UUID getId() {
return id;
}
}