TAMAYA-297: Added tests/small fixes.
Project: http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/repo Commit: http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/commit/ee6133b1 Tree: http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/tree/ee6133b1 Diff: http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/diff/ee6133b1 Branch: refs/heads/master Commit: ee6133b1cd9b5c8f9fb05b80450156764fa7eb99 Parents: 5833662 Author: anatole <[email protected]> Authored: Tue Sep 26 08:43:48 2017 +0200 Committer: anatole <[email protected]> Committed: Tue Sep 26 08:43:48 2017 +0200 ---------------------------------------------------------------------- .../java/org/apache/tamaya/osgi/Backups.java | 9 +- .../org/apache/tamaya/osgi/ConfigHistory.java | 78 ++++++++-- .../apache/tamaya/osgi/TamayaConfigPlugin.java | 86 ++++++----- .../apache/tamaya/osgi/ConfigHistoryTest.java | 148 +++++++++++++++++++ .../java/org/apache/tamaya/osgi/OSGITest.java | 8 - 5 files changed, 275 insertions(+), 54 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/blob/ee6133b1/osgi/common/src/main/java/org/apache/tamaya/osgi/Backups.java ---------------------------------------------------------------------- diff --git a/osgi/common/src/main/java/org/apache/tamaya/osgi/Backups.java b/osgi/common/src/main/java/org/apache/tamaya/osgi/Backups.java index cacf830..01074fd 100644 --- a/osgi/common/src/main/java/org/apache/tamaya/osgi/Backups.java +++ b/osgi/common/src/main/java/org/apache/tamaya/osgi/Backups.java @@ -33,6 +33,7 @@ import java.util.logging.Logger; public final class Backups { private static final Logger LOG = Logger.getLogger(Backups.class.getName()); + public static final String TAMAYA_BACKUP = "tamaya.backup"; private static Map<String, Hashtable<String,?>> initialConfigState = new ConcurrentHashMap<>(); private Backups(){} @@ -81,22 +82,22 @@ public final class Backups { return initialConfigState.containsKey(pid); } - public static void save(TamayaConfigPlugin plugin){ + public static void save(Dictionary<String,Object> config){ try{ ByteArrayOutputStream bos = new ByteArrayOutputStream(); ObjectOutputStream oos = new ObjectOutputStream(bos); oos.writeObject(initialConfigState); oos.flush(); Base64.getEncoder().encode(bos.toByteArray()); - plugin.setConfigValue("backup", Base64.getEncoder().encode(bos.toByteArray())); + config.put(TAMAYA_BACKUP, Base64.getEncoder().encode(bos.toByteArray())); }catch(Exception e){ LOG.log(Level.SEVERE, "Failed to restore OSGI Backups.", e); } } - public static void restore(TamayaConfigPlugin plugin){ + public static void restore(Dictionary<String,Object> config){ try{ - String serialized = (String)plugin.getConfigValue("backup"); + String serialized = (String)config.get("tamaya.backup"); if(serialized!=null) { ByteArrayInputStream bis = new ByteArrayInputStream(Base64.getDecoder().decode(serialized)); ObjectInputStream ois = new ObjectInputStream(bis); http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/blob/ee6133b1/osgi/common/src/main/java/org/apache/tamaya/osgi/ConfigHistory.java ---------------------------------------------------------------------- diff --git a/osgi/common/src/main/java/org/apache/tamaya/osgi/ConfigHistory.java b/osgi/common/src/main/java/org/apache/tamaya/osgi/ConfigHistory.java index 756fe98..8e1b822 100644 --- a/osgi/common/src/main/java/org/apache/tamaya/osgi/ConfigHistory.java +++ b/osgi/common/src/main/java/org/apache/tamaya/osgi/ConfigHistory.java @@ -18,8 +18,6 @@ */ package org.apache.tamaya.osgi; -import java.beans.XMLDecoder; -import java.beans.XMLEncoder; import java.io.*; import java.util.*; import java.util.logging.Level; @@ -33,22 +31,30 @@ public final class ConfigHistory implements Serializable{ private static final long serialVersionUID = 1L; private static final Logger LOG = Logger.getLogger(ConfigHistory.class.getName()); + /** The key of the plugin OSGI configuration, where the history is stored/retrieved. */ + private static final String HISTORY_KEY = "tamaya.history"; public enum TaskType{ PROPERTY, BEGIN, END, } - + /** The max number of changes tracked. */ private static int maxHistory = 10000; + /** The overall history. */ private static List<ConfigHistory> history = new LinkedList<ConfigHistory>(); + /** The entry timestamp. */ private long timestamp = System.currentTimeMillis(); - + /** The entry type. */ private TaskType type; + /** The previous value. */ private Object previousValue; + /** The current value. */ private Object value; + /** The key. */ private String key; + /** The target PID. */ private String pid; private ConfigHistory(TaskType taskType, String pid){ @@ -56,6 +62,12 @@ public final class ConfigHistory implements Serializable{ this.pid = Objects.requireNonNull(pid); } + /** + * Creates and registers an entry when starting to configure a bundle. + * @param pid the PID + * @param info any info. + * @return the entry, never null. + */ public static ConfigHistory configuring(String pid, String info){ ConfigHistory h = new ConfigHistory(TaskType.BEGIN, pid) .setValue(info); @@ -65,6 +77,13 @@ public final class ConfigHistory implements Serializable{ } return h; } + + /** + * Creates and registers an entry when finished to configure a bundle. + * @param pid the PID + * @param info any info. + * @return the entry, never null. + */ public static ConfigHistory configured(String pid, String info){ ConfigHistory h = new ConfigHistory(TaskType.END, pid) .setValue(info); @@ -74,6 +93,15 @@ public final class ConfigHistory implements Serializable{ } return h; } + + /** + * Creates and registers an entry when a property has been changed. + * @param pid the PID + * @param key the key, not null. + * @param previousValue the previous value. + * @param value the new value. + * @return the entry, never null. + */ public static ConfigHistory propertySet(String pid, String key, Object value, Object previousValue){ ConfigHistory h = new ConfigHistory(TaskType.PROPERTY, pid) .setKey(key) @@ -86,22 +114,41 @@ public final class ConfigHistory implements Serializable{ return h; } + /** + * Sets the maximum history size. + * @param maxHistory the size + */ public static void setMaxHistory(int maxHistory){ ConfigHistory.maxHistory = maxHistory; } + /** + * Get the max history size. + * @return the max size + */ public static int getMaxHistory(){ return maxHistory; } + /** + * Access the current history. + * @return the current history, never null. + */ public static List<ConfigHistory> history(){ return history(null); } + /** + * Clears the history. + */ public static void clearHistory(){ clearHistory(null); } + /** + * Ckears the history for a PID. + * @param pid the pid, null clears the full history. + */ public static void clearHistory(String pid){ synchronized (history){ if(pid==null || pid.isEmpty()) { @@ -112,6 +159,11 @@ public final class ConfigHistory implements Serializable{ } } + /** + * Get the history for a PID. + * @param pid the pid, null returns the full history. + * @return + */ public static List<ConfigHistory> history(String pid) { if(pid==null || pid.isEmpty()){ return new ArrayList<>(history); @@ -162,22 +214,30 @@ public final class ConfigHistory implements Serializable{ return this; } - public static void save(TamayaConfigPlugin plugin){ + /** + * This methd saves the (serialized) history in the plugin's OSGI configuration using + * the HISTORY_KEY key. + * @param osgiConfig the plugin config, not null. + */ + public static void save(Dictionary<String,Object> osgiConfig){ try { ByteArrayOutputStream bos = new ByteArrayOutputStream(); ObjectOutputStream oos = new ObjectOutputStream(bos); oos.writeObject(history); oos.flush(); - Base64.getEncoder().encode(bos.toByteArray()); - plugin.setConfigValue("history", Base64.getEncoder().encode(bos.toByteArray())); + osgiConfig.put(HISTORY_KEY, Base64.getEncoder().encodeToString(bos.toByteArray())); } catch (Exception e) { LOG.log(Level.WARNING, "Failed to store getConfig change history.", e); } } - public static void restore(TamayaConfigPlugin plugin){ + /** + * Restores the history from the plugin's OSGI configuration. + * @param osgiConfig + */ + public static void restore(Dictionary<String,Object> osgiConfig){ try{ - String serialized = (String)plugin.getConfigValue("history"); + String serialized = (String)osgiConfig.get(HISTORY_KEY); if(serialized!=null) { ByteArrayInputStream bis = new ByteArrayInputStream(Base64.getDecoder().decode(serialized)); ObjectInputStream ois = new ObjectInputStream(bis); http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/blob/ee6133b1/osgi/common/src/main/java/org/apache/tamaya/osgi/TamayaConfigPlugin.java ---------------------------------------------------------------------- diff --git a/osgi/common/src/main/java/org/apache/tamaya/osgi/TamayaConfigPlugin.java b/osgi/common/src/main/java/org/apache/tamaya/osgi/TamayaConfigPlugin.java index e1aa4a5..0d947fc 100644 --- a/osgi/common/src/main/java/org/apache/tamaya/osgi/TamayaConfigPlugin.java +++ b/osgi/common/src/main/java/org/apache/tamaya/osgi/TamayaConfigPlugin.java @@ -67,11 +67,12 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ */ TamayaConfigPlugin(BundleContext context) { configChanger = new ConfigChanger(context); - Backups.restore(this); - ConfigHistory.restore(this); - initDefaultEnabled(); - initAutoUpdateEnabled(); - initDefaultOpMode(); + Dictionary<String,Object> props = getPluginConfig(); + Backups.restore(props); + ConfigHistory.restore(props); + initDefaultEnabled(props); + initAutoUpdateEnabled(props); + initDefaultOpMode(props); initConfigs(); } @@ -131,8 +132,10 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ return; } configChanger.configure(pid, event.getServiceReference().getBundle(), defaultOpMode, false, false); - Backups.save(this); - ConfigHistory.save(this); + Dictionary<String,Object> props = getPluginConfig(); + Backups.save(props); + ConfigHistory.save(props); + setPluginConfig(props); } public Dictionary<String,Object> updateConfig(String pid) { @@ -149,8 +152,10 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ }else { LOG.fine("Updating getConfig for pid...: " + pid); Dictionary<String,Object> result = configChanger.configure(pid, null, opMode, explicitMode, false); - Backups.save(this); - ConfigHistory.save(this); + Dictionary<String,Object> props = getPluginConfig(); + Backups.save(props); + ConfigHistory.save(props); + setPluginConfig(props); return result; } } @@ -169,8 +174,10 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ return; } configChanger.configure(pid, bundle, defaultOpMode, false, false); - Backups.save(this); - ConfigHistory.save(this); + Dictionary<String,Object> props = getPluginConfig(); + Backups.save(props); + ConfigHistory.save(props); + setPluginConfig(props); } public boolean isBundleEnabled(Bundle bundle){ @@ -191,8 +198,8 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ return true; } - private void initAutoUpdateEnabled() { - Object enabledVal = getConfigValue(TAMAYA_AUTO_UPDATE_ENABLED); + private void initAutoUpdateEnabled(Dictionary<String,Object> props) { + Object enabledVal = props.get(TAMAYA_AUTO_UPDATE_ENABLED); if(enabledVal!=null){ this.autoUpdateEnabled = Boolean.parseBoolean(enabledVal.toString()); } @@ -203,8 +210,8 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ } } - private void initDefaultEnabled() { - Object disabledVal = getConfigValue(TAMAYA_ENABLED); + private void initDefaultEnabled(Dictionary<String,Object> props) { + Object disabledVal = props.get(TAMAYA_ENABLED); if(disabledVal==null && System.getProperty(TAMAYA_ENABLED)!=null){ disabledVal = Boolean.parseBoolean(System.getProperty(TAMAYA_ENABLED)); } @@ -218,8 +225,8 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ } } - private void initDefaultOpMode() { - String opVal = (String)getConfigValue(OperationMode.class.getName()); + private void initDefaultOpMode(Dictionary<String,Object> props) { + String opVal = (String)props.get(OperationMode.class.getName()); if(opVal!=null){ try{ defaultOpMode = OperationMode.valueOf(opVal); @@ -229,8 +236,7 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ } } - - void setConfigValue(String key, Object value){ + Dictionary<String, Object> getPluginConfig(){ Configuration config = null; try { config = configChanger.getConfigurationAdmin().getConfiguration(COMPONENTID); @@ -241,31 +247,45 @@ public class TamayaConfigPlugin implements BundleListener, ServiceListener{ } else { props = new Hashtable<String, Object>(); } - Object val = props.get(key); - if(val==null) { - props.put(key, value); - config.update(props); - } - LOG.finest("Updated Tamaya Plugin getConfig: "+key + "=" + value); + return props; } catch (IOException e) { - LOG.log(Level.WARNING, "Error writing Tamaya getConfig.", e); + throw new IllegalStateException("No Tamaya plugin config.", e); } } - Object getConfigValue(String key){ + void setPluginConfig(Dictionary<String, Object> props){ Configuration config = null; try { config = configChanger.getConfigurationAdmin().getConfiguration(COMPONENTID); - Dictionary<String, Object> props = null; - if (config != null - && config.getProperties() != null) { - props = config.getProperties(); + if (config != null) { + config.update(props); + } + } catch (IOException e) { + LOG.log(Level.WARNING, "Failed to write Tamaya plugin config.", e); + } + } + + void setConfigValue(String key, Object value){ + try { + Dictionary<String, Object> props = getPluginConfig(); + if(props!=null) { + props.put(key, value); + setPluginConfig(props); + LOG.finest("Updated Tamaya Plugin value: " + key + "=" + value); } + } catch (Exception e) { + LOG.log(Level.WARNING, "Error writing Tamaya config value: " + key, e); + } + } + + Object getConfigValue(String key){ + try { + Dictionary<String, Object> props = getPluginConfig(); if(props!=null){ return props.get(key); } - } catch (IOException e) { - LOG.log(Level.WARNING, "Error reading Tamaya getConfig.", e); + } catch (Exception e) { + LOG.log(Level.WARNING, "Error reading Tamaya config value.", e); } return null; } http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/blob/ee6133b1/osgi/common/src/test/java/org/apache/tamaya/osgi/ConfigHistoryTest.java ---------------------------------------------------------------------- diff --git a/osgi/common/src/test/java/org/apache/tamaya/osgi/ConfigHistoryTest.java b/osgi/common/src/test/java/org/apache/tamaya/osgi/ConfigHistoryTest.java new file mode 100644 index 0000000..7e58176 --- /dev/null +++ b/osgi/common/src/test/java/org/apache/tamaya/osgi/ConfigHistoryTest.java @@ -0,0 +1,148 @@ +/* + * 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.osgi; + +import org.junit.Test; + +import java.util.Dictionary; +import java.util.Hashtable; +import java.util.List; + +import static org.junit.Assert.*; + + +/** + * Created by atsticks on 26.09.17. + */ +public class ConfigHistoryTest { + @Test + public void configuring() throws Exception { + ConfigHistory en = ConfigHistory.configuring("configuring", "configuring_test"); + assertNotNull(en); + assertEquals(en.getPid(), "configuring"); + assertEquals(en.getType(), ConfigHistory.TaskType.BEGIN); + assertEquals(en.getValue(), "configuring_test"); + } + + @Test + public void configured() throws Exception { + ConfigHistory en = ConfigHistory.configured("configured", "configured_test"); + assertNotNull(en); + assertEquals(en.getPid(), "configured"); + assertEquals(en.getType(), ConfigHistory.TaskType.END); + assertEquals(en.getValue(), "configured_test"); + } + + @Test + public void propertySet() throws Exception { + ConfigHistory en = ConfigHistory.propertySet("propertySet", "propertySet.key", "new", "prev"); + assertNotNull(en); + assertEquals(en.getPid(), "propertySet"); + assertEquals(en.getType(), ConfigHistory.TaskType.PROPERTY); + assertEquals(en.getKey(), "propertySet.key"); + assertEquals(en.getPreviousValue(), "prev"); + assertEquals(en.getValue(),"new"); + } + + @Test + public void setGetMaxHistory() throws Exception { + ConfigHistory.setMaxHistory(1000); + assertEquals(ConfigHistory.getMaxHistory(),1000); + } + + @Test + public void history() throws Exception { + for(int i=0;i<100;i++){ + ConfigHistory.propertySet("history", "history"+i, "prev"+i, "new"+i); + } + List<ConfigHistory> hist = ConfigHistory.history(); + assertNotNull(hist); + assertTrue(hist.size()>=100); + } + + @Test + public void history_pid() throws Exception { + ConfigHistory.configuring("history1", "history_pid"); + for(int i=0;i<100;i++){ + ConfigHistory.propertySet("history1", "history"+i, "prev"+i, "new"+i); + } + ConfigHistory.configured("history1", "history_pid"); + for(int i=0;i<100;i++){ + ConfigHistory.propertySet("history2", "history"+i, "prev"+i, "new"+i); + } + List<ConfigHistory> hist = ConfigHistory.history("history1"); + assertNotNull(hist); + assertTrue(hist.size()==102); + hist = ConfigHistory.history("history2"); + assertNotNull(hist); + assertTrue(hist.size()==100); + hist = ConfigHistory.history(null); + assertNotNull(hist); + assertTrue(hist.size()>=202); + } + + @Test + public void clearHistory() throws Exception { + for(int i=0;i<100;i++){ + ConfigHistory.propertySet("history3", "history"+i, "prev"+i, "new"+i); + } + for(int i=0;i<100;i++){ + ConfigHistory.propertySet("history4", "history"+i, "prev"+i, "new"+i); + } + List<ConfigHistory> hist = ConfigHistory.history("history3"); + assertNotNull(hist); + assertTrue(hist.size()==100); + assertEquals(ConfigHistory.history("history4").size(), 100); + ConfigHistory.clearHistory("history3"); + assertEquals(ConfigHistory.history("history3").size(), 0); + assertEquals(ConfigHistory.history("history4").size(), 100); + ConfigHistory.clearHistory(null); + assertEquals(ConfigHistory.history().size(), 0); + assertEquals(ConfigHistory.history("history4").size(), 0); + } + + + @Test + public void setPreviousValue() throws Exception { + } + + @Test + public void getValue() throws Exception { + } + + @Test + public void getKey() throws Exception { + } + + @Test + public void saveRestore() throws Exception { + for(int i=0;i<10;i++){ + ConfigHistory.propertySet("save", "history"+i, "prev"+i, "new"+i); + } + assertEquals(ConfigHistory.history("save").size(), 10); + Dictionary<String,Object> config = new Hashtable<>(); + ConfigHistory.save(config); + assertEquals(ConfigHistory.history("save").size(), 10); + ConfigHistory.clearHistory(); + assertEquals(ConfigHistory.history("save").size(), 0); + ConfigHistory.restore(config); + assertEquals(ConfigHistory.history("save").size(), 10); + } + +} \ No newline at end of file http://git-wip-us.apache.org/repos/asf/incubator-tamaya-sandbox/blob/ee6133b1/osgi/common/src/test/java/org/apache/tamaya/osgi/OSGITest.java ---------------------------------------------------------------------- diff --git a/osgi/common/src/test/java/org/apache/tamaya/osgi/OSGITest.java b/osgi/common/src/test/java/org/apache/tamaya/osgi/OSGITest.java index 1c5b959..8cfa72d 100644 --- a/osgi/common/src/test/java/org/apache/tamaya/osgi/OSGITest.java +++ b/osgi/common/src/test/java/org/apache/tamaya/osgi/OSGITest.java @@ -102,14 +102,6 @@ public class OSGITest { } @Test - public void ensureEnvironmentIsWorkingAndTamayaIsActive()throws Exception { - assertNotNull(configAdmin); - assertEquals("Tamaya ConfigAdmin is not installed.", - "TamayaConfigAdminImpl", configAdmin.getClass().getSimpleName()); - System.out.println("ConfigAdmin found in OSGI Container: " + configAdmin); - } - - @Test public void testResourceIsVisible(){ assertNotNull(ServiceContextManager.getServiceContext() .getResource("META-INF/javaconfiguration.properties", null));
