Repository: incubator-tamaya Updated Branches: refs/heads/master 574332226 -> 0734e210e
TAMAYA-38 implemented standard System- and EnvironmentPropertySource Project: http://git-wip-us.apache.org/repos/asf/incubator-tamaya/repo Commit: http://git-wip-us.apache.org/repos/asf/incubator-tamaya/commit/51960ef0 Tree: http://git-wip-us.apache.org/repos/asf/incubator-tamaya/tree/51960ef0 Diff: http://git-wip-us.apache.org/repos/asf/incubator-tamaya/diff/51960ef0 Branch: refs/heads/master Commit: 51960ef0f1fe507cb894228b1097d35e4d7d077a Parents: 0791e87 Author: Reinhard Sandtner <reinhard.sandt...@gmail.com> Authored: Fri Jan 2 19:40:19 2015 +0100 Committer: Reinhard Sandtner <reinhard.sandt...@gmail.com> Committed: Sat Jan 3 13:18:49 2015 +0100 ---------------------------------------------------------------------- .../org/apache/tamaya/spi/PropertySource.java | 7 ++ core/pom.xml | 5 + .../core/propertysource/BasePropertySource.java | 76 +++++++++++++ .../core/propertysource/DefaultOrdinal.java | 46 ++++++++ .../EnvironmentPropertySource.java | 47 ++++++++ .../propertysource/SystemPropertySource.java | 82 ++++++++++++++ .../propertysource/BasePropertySourceTest.java | 107 +++++++++++++++++++ .../EnvironmentPropertySourceTest.java | 70 ++++++++++++ .../SystemPropertySourceTest.java | 103 ++++++++++++++++++ 9 files changed, 543 insertions(+) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/api/src/main/java/org/apache/tamaya/spi/PropertySource.java ---------------------------------------------------------------------- diff --git a/api/src/main/java/org/apache/tamaya/spi/PropertySource.java b/api/src/main/java/org/apache/tamaya/spi/PropertySource.java index 711b84b..eb11358 100644 --- a/api/src/main/java/org/apache/tamaya/spi/PropertySource.java +++ b/api/src/main/java/org/apache/tamaya/spi/PropertySource.java @@ -48,6 +48,12 @@ import java.util.Optional; public interface PropertySource { /** + * property name to override default tamaya ordinals + */ + static final String TAMAYA_ORDINAL = "tamaya.ordinal"; + + + /** * Lookup order: * TODO rethink whole default PropertySources and ordering: * TODO introduce default values or constants for ordinals @@ -88,6 +94,7 @@ public interface PropertySource { /** * Access a property. * + * //X TODO discuss if the key can be null * @param key the property's key, not null. * @return the property's keys. */ http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/pom.xml ---------------------------------------------------------------------- diff --git a/core/pom.xml b/core/pom.xml index 26ccce0..917f2e2 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -36,6 +36,11 @@ under the License. <artifactId>tamaya-api</artifactId> <version>${project.version}</version> </dependency> + + <dependency> + <groupId>junit</groupId> + <artifactId>junit</artifactId> + </dependency> </dependencies> </project> http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/main/java/org/apache/tamaya/core/propertysource/BasePropertySource.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/tamaya/core/propertysource/BasePropertySource.java b/core/src/main/java/org/apache/tamaya/core/propertysource/BasePropertySource.java new file mode 100644 index 0000000..2a0107c --- /dev/null +++ b/core/src/main/java/org/apache/tamaya/core/propertysource/BasePropertySource.java @@ -0,0 +1,76 @@ +/* + * 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.core.propertysource; + +import org.apache.tamaya.spi.PropertySource; + +import java.util.Objects; +import java.util.Optional; +import java.util.logging.Level; +import java.util.logging.Logger; + +/** + * Base class for {@link PropertySource}s + */ +public abstract class BasePropertySource implements PropertySource { + + private static final Logger LOG = Logger.getLogger(BasePropertySource.class.getName()); + + + private int ordinal = DefaultOrdinal.PROPERTY_SOURCE; + + + @Override + public int getOrdinal() { + return ordinal; + } + + + @Override + public Optional<String> get(String key) { + Objects.requireNonNull(key, "key must not be null"); + return Optional.ofNullable(getProperties().get(key)); + } + + + /** + * Initializing the ordinal of this {@link PropertySource} with the given defaultOrdinal. + * + * If {@link PropertySource#TAMAYA_ORDINAL} is present via {@link #get(String)} and the + * value is a valid {@link Integer} then, the defaultOrdinal will be overridden. + * + * @param defaultOrdinal of the {@link PropertySource} + */ + protected void initialzeOrdinal(final int defaultOrdinal) { + this.ordinal = defaultOrdinal; + + Optional<String> ordinal = get(PropertySource.TAMAYA_ORDINAL); + if (ordinal.isPresent()) { + + try { + this.ordinal = Integer.valueOf(ordinal.get()); + } catch (NumberFormatException e) { + LOG.log(Level.WARNING, + "Specified {0} is not a valid Integer value: {1} - using defaultOrdinal {2}", + new Object[]{PropertySource.TAMAYA_ORDINAL, ordinal.get(), defaultOrdinal}); + } + } + } + +} http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/main/java/org/apache/tamaya/core/propertysource/DefaultOrdinal.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/tamaya/core/propertysource/DefaultOrdinal.java b/core/src/main/java/org/apache/tamaya/core/propertysource/DefaultOrdinal.java new file mode 100644 index 0000000..43b3fad --- /dev/null +++ b/core/src/main/java/org/apache/tamaya/core/propertysource/DefaultOrdinal.java @@ -0,0 +1,46 @@ +/* + * 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.core.propertysource; + + +/** + * This interface defines the default ordinals for the 'standard' + * {@link org.apache.tamaya.spi.PropertySource}s + * + * DefaultOrdinals can be overwritten via {@link org.apache.tamaya.spi.PropertySource#TAMAYA_ORDINAL} + */ +public interface DefaultOrdinal { + + /** + * default ordinal for {@link org.apache.tamaya.core.propertysource.BasePropertySource} if + * not overriden in each class + */ + static final int PROPERTY_SOURCE = 1000; + + /** + * default ordinal for {@link org.apache.tamaya.core.propertysource.SystemPropertySource} + */ + static final int SYSTEM_PROPERTIES = 400; + + /** + * default ordinal for {@link org.apache.tamaya.core.propertysource.EnvironmentPropertySource} + */ + static final int ENVIRONMENT_PROPERTIES = 300; + +} http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/main/java/org/apache/tamaya/core/propertysource/EnvironmentPropertySource.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/tamaya/core/propertysource/EnvironmentPropertySource.java b/core/src/main/java/org/apache/tamaya/core/propertysource/EnvironmentPropertySource.java new file mode 100644 index 0000000..d1a00f4 --- /dev/null +++ b/core/src/main/java/org/apache/tamaya/core/propertysource/EnvironmentPropertySource.java @@ -0,0 +1,47 @@ +/* + * 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.core.propertysource; + +import java.util.Map; + +/** + * This {@link org.apache.tamaya.spi.PropertySource} provides all Properties which are set + * via <br /> + * {@code export myprop=myval} on UNIX Systems or<br /> + * {@code set myprop=myval} on Windows + */ +public class EnvironmentPropertySource extends BasePropertySource { + + public EnvironmentPropertySource() { + initialzeOrdinal(DefaultOrdinal.ENVIRONMENT_PROPERTIES); + } + + + @Override + public String getName() { + return "environment-properties"; + } + + @Override + public Map<String, String> getProperties() { + return System.getenv(); // already a map and unmodifiable + + } + +} http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/main/java/org/apache/tamaya/core/propertysource/SystemPropertySource.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/tamaya/core/propertysource/SystemPropertySource.java b/core/src/main/java/org/apache/tamaya/core/propertysource/SystemPropertySource.java new file mode 100644 index 0000000..afd9f93 --- /dev/null +++ b/core/src/main/java/org/apache/tamaya/core/propertysource/SystemPropertySource.java @@ -0,0 +1,82 @@ +/* + * 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.core.propertysource; + +import java.util.Collections; +import java.util.HashMap; +import java.util.Map; +import java.util.Properties; + +/** + * This {@link org.apache.tamaya.spi.PropertySource} manages the system properties. + */ +public class SystemPropertySource extends BasePropertySource { + + + //X TODO disuss default ordinal of SystemProperties + + + /** + * cashed System.getProperties() filled in our Map + */ + private Map<String, String> properties; + + /** + * previous System.getProperties().hashCode() + * so we can check if we need to reload + */ + private int previousHash; + + + public SystemPropertySource() { + initialzeOrdinal(DefaultOrdinal.SYSTEM_PROPERTIES); + } + + + @Override + public String getName() { + return "system-properties"; + } + + @Override + public Map<String, String> getProperties() { + + // only need to reload and fill our map if something has changed + if (properties == null || previousHash != System.getProperties().hashCode()) { + + synchronized (this) { + + if (properties == null || previousHash != System.getProperties().hashCode()) { + + Properties systemProperties = System.getProperties(); + Map<String, String> properties = new HashMap<>(); + + for (String propertyName : systemProperties.stringPropertyNames()) { + properties.put(propertyName, System.getProperty(propertyName)); + } + + this.properties = Collections.unmodifiableMap(properties); + previousHash = systemProperties.hashCode(); + } + } + } + + return properties; + } +} http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/test/java/org/apache/tamaya/core/test/propertysource/BasePropertySourceTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/org/apache/tamaya/core/test/propertysource/BasePropertySourceTest.java b/core/src/test/java/org/apache/tamaya/core/test/propertysource/BasePropertySourceTest.java new file mode 100644 index 0000000..7b92910 --- /dev/null +++ b/core/src/test/java/org/apache/tamaya/core/test/propertysource/BasePropertySourceTest.java @@ -0,0 +1,107 @@ +/* + * 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.core.test.propertysource; + +import org.apache.tamaya.core.propertysource.BasePropertySource; +import org.apache.tamaya.core.propertysource.DefaultOrdinal; +import org.apache.tamaya.spi.PropertySource; +import org.junit.Assert; +import org.junit.Test; + +import java.util.Collections; +import java.util.HashMap; +import java.util.Map; +import java.util.Optional; +import java.util.Properties; + +public class BasePropertySourceTest { + + @Test + public void testGetOrdinal() { + + PropertySource defaultPropertySource = new BasePropertySource() { + + @Override + public String getName() { + return "testWithDefault"; + } + + @Override + public Optional<String> get(String key) { + return Optional.ofNullable(null); + } + + @Override + public Map<String, String> getProperties() { + return Collections.emptyMap(); + } + }; + + Assert.assertEquals(DefaultOrdinal.PROPERTY_SOURCE, defaultPropertySource.getOrdinal()); + Assert.assertEquals(1000, new OverriddenOrdinalPropertySource().getOrdinal()); + + // propertySource with invalid ordinal + Assert.assertEquals(1, new OverriddenInvalidOrdinalPropertySource().getOrdinal()); + } + + @Test + public void testGet() { + Assert.assertEquals("1000", new OverriddenOrdinalPropertySource().get(PropertySource.TAMAYA_ORDINAL).get()); + } + + private static class OverriddenOrdinalPropertySource extends BasePropertySource { + + private OverriddenOrdinalPropertySource() { + initialzeOrdinal(250); + } + + @Override + public String getName() { + return "overriddenOrdinal"; + } + + @Override + public Map<String, String> getProperties() { + Map<String, String> map = new HashMap<>(1); + map.put(PropertySource.TAMAYA_ORDINAL, "1000"); + return map; + } + } + + private static class OverriddenInvalidOrdinalPropertySource extends BasePropertySource { + + private OverriddenInvalidOrdinalPropertySource() { + initialzeOrdinal(1); + } + + @Override + public String getName() { + return "overriddenInvalidOrdinal"; + } + + @Override + public Map<String, String> getProperties() { + Map<String, String> map = new HashMap<>(1); + map.put(PropertySource.TAMAYA_ORDINAL, "invalid"); + return map; + } + } + + +} http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/test/java/org/apache/tamaya/core/test/propertysource/EnvironmentPropertySourceTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/org/apache/tamaya/core/test/propertysource/EnvironmentPropertySourceTest.java b/core/src/test/java/org/apache/tamaya/core/test/propertysource/EnvironmentPropertySourceTest.java new file mode 100644 index 0000000..51cc2dc --- /dev/null +++ b/core/src/test/java/org/apache/tamaya/core/test/propertysource/EnvironmentPropertySourceTest.java @@ -0,0 +1,70 @@ +/* + * 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.core.test.propertysource; + +import org.apache.tamaya.core.propertysource.DefaultOrdinal; +import org.apache.tamaya.core.propertysource.EnvironmentPropertySource; +import org.junit.Assert; +import org.junit.Test; + +import java.util.Map; +import java.util.Optional; + +public class EnvironmentPropertySourceTest { + + private EnvironmentPropertySource propertySource = new EnvironmentPropertySource(); + + + @Test + public void testGetOrdinal() { + Assert.assertEquals(DefaultOrdinal.ENVIRONMENT_PROPERTIES, propertySource.getOrdinal()); + } + + @Test + public void testGet() { + String environmentPropertyToCheck = System.getenv().keySet().iterator().next(); + + Optional<String> value = propertySource.get(environmentPropertyToCheck); + Assert.assertTrue(value.isPresent()); + Assert.assertEquals(System.getenv(environmentPropertyToCheck), value.get()); + } + + @Test + public void testGetProperties() { + Map<String, String> environmentProperties = System.getenv(); + + Assert.assertEquals(environmentProperties.size(), propertySource.getProperties().size()); + + for (Map.Entry<String, String> propertySourceEntry : propertySource.getProperties().entrySet()) { + Assert.assertEquals("Entry values for key '" + propertySourceEntry.getKey() + "' do not match", + environmentProperties.get(propertySourceEntry.getKey()), propertySourceEntry.getValue()); + } + + // modification is not allowed + try { + propertySource.getProperties().put("add.new.keys", "must throw exception"); + Assert.fail(UnsupportedOperationException.class.getName() + " expected"); + } + catch (UnsupportedOperationException e) { + // expected -> all is fine + } + } + + +} http://git-wip-us.apache.org/repos/asf/incubator-tamaya/blob/51960ef0/core/src/test/java/org/apache/tamaya/core/test/propertysource/SystemPropertySourceTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/org/apache/tamaya/core/test/propertysource/SystemPropertySourceTest.java b/core/src/test/java/org/apache/tamaya/core/test/propertysource/SystemPropertySourceTest.java new file mode 100644 index 0000000..5789346 --- /dev/null +++ b/core/src/test/java/org/apache/tamaya/core/test/propertysource/SystemPropertySourceTest.java @@ -0,0 +1,103 @@ +/* + * 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.core.test.propertysource; + +import org.apache.tamaya.core.propertysource.DefaultOrdinal; +import org.apache.tamaya.core.propertysource.SystemPropertySource; +import org.apache.tamaya.spi.PropertySource; +import org.junit.Assert; +import org.junit.Test; + +import java.util.Map; +import java.util.Optional; +import java.util.Properties; +import java.util.Set; + +public class SystemPropertySourceTest { + + private SystemPropertySource testPropertySource = new SystemPropertySource(); + + + @Test + public void testGetOrdinal() throws Exception { + + // test the default ordinal + Assert.assertEquals(DefaultOrdinal.SYSTEM_PROPERTIES, testPropertySource.getOrdinal()); + + // set the ordinal to 1000 + System.setProperty(PropertySource.TAMAYA_ORDINAL, "1000"); + Assert.assertEquals(1000, new SystemPropertySource().getOrdinal()); // currently its not possible to change ordinal at runtime + + // reset it to not destroy other tests!! + System.clearProperty(PropertySource.TAMAYA_ORDINAL); + } + + @Test + public void testGetName() throws Exception { + Assert.assertEquals("system-properties", new SystemPropertySource().getName()); + } + + @Test + public void testGet() throws Exception { + String propertyKeyToCheck = System.getProperties().stringPropertyNames().iterator().next(); + + Optional<String> property = testPropertySource.get(propertyKeyToCheck); + Assert.assertTrue("Property '" + propertyKeyToCheck + "' is not present in " + SystemPropertySource.class.getSimpleName(), + property.isPresent()); + Assert.assertEquals(System.getProperty(propertyKeyToCheck), property.get()); + + + } + + @Test + public void testGetProperties() throws Exception { + checkWithSystemProperties(testPropertySource.getProperties()); + + // modify system properties + System.setProperty("test", "myTestVal"); + + checkWithSystemProperties(testPropertySource.getProperties()); + + // cleanup + System.clearProperty("test"); + + // no modifaction + try { + testPropertySource.getProperties().put("add.new.keys", "must throw exception"); + Assert.fail(UnsupportedOperationException.class.getName() + " expected"); + } + catch (UnsupportedOperationException e) { + // expected -> all is fine + } + } + + private void checkWithSystemProperties(Map<String, String> toCheck) { + Properties systemEntries = System.getProperties(); + + Assert.assertEquals("size of System.getProperties().entrySet() must be the same as SystemPropertySrouce.getProperties().entrySet()", + systemEntries.entrySet().size(), toCheck.size()); + + for (Map.Entry<String, String> propertySourceEntry : toCheck.entrySet()) { + + Assert.assertEquals("Entry values for key '" + propertySourceEntry.getKey() + "' do not match", + systemEntries.getProperty(propertySourceEntry.getKey()), propertySourceEntry.getValue()); + } + + } +} \ No newline at end of file