This is an automated email from the ASF dual-hosted git repository. ggregory pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/commons-collections.git
The following commit(s) were added to refs/heads/master by this push: new d5bf768 [COLLECTIONS-748] Let org.apache.commons.collections4.properties.[Sorted]PropertiesFactory accept XML input. d5bf768 is described below commit d5bf76870f507944d5e0e68ce77d8ac974968c03 Author: Gary Gregory <garydgreg...@gmail.com> AuthorDate: Sun Feb 16 20:42:27 2020 -0500 [COLLECTIONS-748] Let org.apache.commons.collections4.properties.[Sorted]PropertiesFactory accept XML input. --- src/changes/changes.xml | 3 ++ .../properties/AbstractPropertiesFactory.java | 52 +++++++++++++++++++-- .../properties/AbstractPropertiesFactoryTest.java | 54 +++++++++++++++++----- .../properties/PropertiesFactoryTest.java | 4 +- .../properties/SortedPropertiesFactoryTest.java | 4 +- src/test/resources/properties/test.xml | 32 +++++++++++++ 6 files changed, 129 insertions(+), 20 deletions(-) diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 5ad5517..578ed5a 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -132,6 +132,9 @@ <action issue="COLLECTIONS-747" dev="ggregory" type="fix" due-to="Gary Gregory, Walter Laan"> MultiKey.getKeys class cast exception. </action> + <action issue="COLLECTIONS-748" dev="ggregory" type="update" due-to="Gary Gregory"> + Let org.apache.commons.collections4.properties.[Sorted]PropertiesFactory accept XML input. + </action> </release> <release version="4.4" date="2019-07-05" description="Maintenance release."> <action issue="COLLECTIONS-710" dev="ggregory" type="fix" due-to="Yu Shi, Gary Gregory"> diff --git a/src/main/java/org/apache/commons/collections4/properties/AbstractPropertiesFactory.java b/src/main/java/org/apache/commons/collections4/properties/AbstractPropertiesFactory.java index 7c89f60..249905b 100644 --- a/src/main/java/org/apache/commons/collections4/properties/AbstractPropertiesFactory.java +++ b/src/main/java/org/apache/commons/collections4/properties/AbstractPropertiesFactory.java @@ -28,6 +28,7 @@ import java.net.URL; import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; +import java.util.Objects; import java.util.Properties; /** @@ -39,6 +40,24 @@ import java.util.Properties; */ public abstract class AbstractPropertiesFactory<T extends Properties> { + /** + * Enumerat5es property formats. + * + * @since 4.5 + */ + public enum PropertyFormat { + + /** Properties file format. */ + PROPERTIES, + + /** XML file format. */ + XML; + + static PropertyFormat toPropertyFormat(String fileName) { + return Objects.requireNonNull(fileName, "fileName").endsWith(".xml") ? XML : PROPERTIES; + } + } + /** * Constructs an instance. */ @@ -64,7 +83,7 @@ public abstract class AbstractPropertiesFactory<T extends Properties> { */ public T load(final ClassLoader classLoader, final String name) throws IOException { try (final InputStream inputStream = classLoader.getResourceAsStream(name)) { - return load(inputStream); + return load(inputStream, PropertyFormat.toPropertyFormat(name)); } } @@ -82,7 +101,7 @@ public abstract class AbstractPropertiesFactory<T extends Properties> { */ public T load(final File file) throws FileNotFoundException, IOException { try (final FileInputStream inputStream = new FileInputStream(file)) { - return load(inputStream); + return load(inputStream, PropertyFormat.toPropertyFormat(file.getName())); } } @@ -104,6 +123,29 @@ public abstract class AbstractPropertiesFactory<T extends Properties> { } /** + * Creates and loads properties from the given input stream. + * + * @param inputStream the location of the properties file. + * @param propertyFormat The format of the given file. + * @return a new properties object. + * @throws IOException Thrown if an error occurred reading the input stream. + * @throws IllegalArgumentException Thrown if the input contains a malformed Unicode escape sequence. + * @since 4.5 + */ + public T load(final InputStream inputStream, final PropertyFormat propertyFormat) throws IOException { + if (inputStream == null) { + return null; + } + final T properties = createProperties(); + if (propertyFormat == PropertyFormat.XML) { + properties.loadFromXML(inputStream); + } else { + properties.load(inputStream); + } + return properties; + } + + /** * Creates and loads properties from the given path. * * @param path the location of the properties file. @@ -113,7 +155,7 @@ public abstract class AbstractPropertiesFactory<T extends Properties> { */ public T load(final Path path) throws IOException { try (final InputStream inputStream = Files.newInputStream(path)) { - return load(inputStream); + return load(inputStream, PropertyFormat.toPropertyFormat(Objects.toString(path.getFileName(), null))); } } @@ -141,7 +183,7 @@ public abstract class AbstractPropertiesFactory<T extends Properties> { */ public T load(final String name) throws IOException { try (final FileInputStream inputStream = new FileInputStream(name)) { - return load(inputStream); + return load(inputStream, PropertyFormat.toPropertyFormat(name)); } } @@ -167,7 +209,7 @@ public abstract class AbstractPropertiesFactory<T extends Properties> { */ public T load(final URL url) throws IOException { try (final InputStream inputStream = url.openStream()) { - return load(inputStream); + return load(inputStream, PropertyFormat.toPropertyFormat(url.getFile())); } } diff --git a/src/test/java/org/apache/commons/collections4/properties/AbstractPropertiesFactoryTest.java b/src/test/java/org/apache/commons/collections4/properties/AbstractPropertiesFactoryTest.java index 3e68a65..2ea6a07 100644 --- a/src/test/java/org/apache/commons/collections4/properties/AbstractPropertiesFactoryTest.java +++ b/src/test/java/org/apache/commons/collections4/properties/AbstractPropertiesFactoryTest.java @@ -24,22 +24,48 @@ import java.nio.file.Paths; import java.util.Properties; import org.junit.Assert; +import org.junit.Assume; import org.junit.Test; +import org.junit.runner.RunWith; +import org.junit.runners.Parameterized; +import org.junit.runners.Parameterized.Parameters; +@RunWith(Parameterized.class) public abstract class AbstractPropertiesFactoryTest<T extends Properties> { - private static final String PATH_STRING = "src/test/resources/properties/test.properties"; + @Parameters(name = "{0}") + public static Object[][] getParameters() { + return new Object[][] { { ".properties" }, { ".xml" } }; + + } private final AbstractPropertiesFactory<T> factory; + private final String pathString; + private final String fileExtention; - protected AbstractPropertiesFactoryTest(final AbstractPropertiesFactory<T> factory) { + protected AbstractPropertiesFactoryTest(final AbstractPropertiesFactory<T> factory, final String fileExtension) { super(); this.factory = factory; + this.fileExtention = fileExtension; + this.pathString = "src/test/resources/properties/test" + fileExtention; } private void assertContents(final T properties) { Assert.assertEquals("value1", properties.getProperty("key1")); Assert.assertEquals("value2", properties.getProperty("key2")); + Assert.assertEquals("value3", properties.getProperty("key3")); + Assert.assertEquals("value4", properties.getProperty("key4")); + Assert.assertEquals("value5", properties.getProperty("key5")); + Assert.assertEquals("value6", properties.getProperty("key6")); + Assert.assertEquals("value7", properties.getProperty("key7")); + Assert.assertEquals("value8", properties.getProperty("key8")); + Assert.assertEquals("value9", properties.getProperty("key9")); + Assert.assertEquals("value10", properties.getProperty("key10")); + Assert.assertEquals("value11", properties.getProperty("key11")); + } + + private boolean isXmlTest() { + return ".xml".equals(fileExtention); } @Test @@ -49,50 +75,56 @@ public abstract class AbstractPropertiesFactoryTest<T extends Properties> { @Test public void testLoadClassLoaderMissingResource() throws Exception { - Assert.assertNull(factory.load(ClassLoader.getSystemClassLoader(), "missing/test.properties")); + Assert.assertNull(factory.load(ClassLoader.getSystemClassLoader(), "missing/test" + fileExtention)); } @Test public void testLoadClassLoaderResource() throws Exception { - assertContents(factory.load(ClassLoader.getSystemClassLoader(), "properties/test.properties")); + assertContents(factory.load(ClassLoader.getSystemClassLoader(), "properties/test" + fileExtention)); } @Test public void testLoadFile() throws Exception { - assertContents(factory.load(Paths.get(PATH_STRING).toFile())); + assertContents(factory.load(Paths.get(pathString).toFile())); } @Test public void testLoadFileName() throws Exception { - assertContents(factory.load(PATH_STRING)); + assertContents(factory.load(pathString)); } @Test public void testLoadInputStream() throws Exception { - try (final FileInputStream inputStream = new FileInputStream(PATH_STRING)) { + // Can't tell what we are reading + Assume.assumeFalse(isXmlTest()); + // + try (final FileInputStream inputStream = new FileInputStream(pathString)) { assertContents(factory.load(inputStream)); } } @Test public void testLoadPath() throws Exception { - assertContents(factory.load(Paths.get(PATH_STRING))); + assertContents(factory.load(Paths.get(pathString))); } @Test public void testLoadReader() throws Exception { - try (final BufferedReader inputStream = Files.newBufferedReader(Paths.get(PATH_STRING))) { + // Can't tell what we are reading + Assume.assumeFalse(isXmlTest()); + // + try (final BufferedReader inputStream = Files.newBufferedReader(Paths.get(pathString))) { assertContents(factory.load(inputStream)); } } @Test public void testLoadUri() throws Exception { - assertContents(factory.load(Paths.get(PATH_STRING).toUri())); + assertContents(factory.load(Paths.get(pathString).toUri())); } @Test public void testLoadUrl() throws Exception { - assertContents(factory.load(Paths.get(PATH_STRING).toUri().toURL())); + assertContents(factory.load(Paths.get(pathString).toUri().toURL())); } } diff --git a/src/test/java/org/apache/commons/collections4/properties/PropertiesFactoryTest.java b/src/test/java/org/apache/commons/collections4/properties/PropertiesFactoryTest.java index 83133d0..ddfe40a 100644 --- a/src/test/java/org/apache/commons/collections4/properties/PropertiesFactoryTest.java +++ b/src/test/java/org/apache/commons/collections4/properties/PropertiesFactoryTest.java @@ -24,8 +24,8 @@ import org.junit.Test; public class PropertiesFactoryTest extends AbstractPropertiesFactoryTest<Properties> { - public PropertiesFactoryTest() { - super(PropertiesFactory.INSTANCE); + public PropertiesFactoryTest(final String fileExtension) { + super(PropertiesFactory.INSTANCE, fileExtension); } @Override diff --git a/src/test/java/org/apache/commons/collections4/properties/SortedPropertiesFactoryTest.java b/src/test/java/org/apache/commons/collections4/properties/SortedPropertiesFactoryTest.java index 19e1429..8f81612 100644 --- a/src/test/java/org/apache/commons/collections4/properties/SortedPropertiesFactoryTest.java +++ b/src/test/java/org/apache/commons/collections4/properties/SortedPropertiesFactoryTest.java @@ -22,8 +22,8 @@ import org.junit.Test; public class SortedPropertiesFactoryTest extends AbstractPropertiesFactoryTest<SortedProperties> { - public SortedPropertiesFactoryTest() { - super(SortedPropertiesFactory.INSTANCE); + public SortedPropertiesFactoryTest(final String fileExtension) { + super(SortedPropertiesFactory.INSTANCE, fileExtension); } @Override diff --git a/src/test/resources/properties/test.xml b/src/test/resources/properties/test.xml new file mode 100644 index 0000000..8e7699e --- /dev/null +++ b/src/test/resources/properties/test.xml @@ -0,0 +1,32 @@ +<?xml version="1.0" encoding="UTF-8" standalone="no"?> +<!-- + 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. +--> +<!DOCTYPE properties SYSTEM "http://java.sun.com/dtd/properties.dtd"> +<properties> + <comment>Hello comment!</comment> + <entry key="key1">value1</entry> + <entry key="key2">value2</entry> + <entry key="key3">value3</entry> + <entry key="key4">value4</entry> + <entry key="key5">value5</entry> + <entry key="key6">value6</entry> + <entry key="key7">value7</entry> + <entry key="key8">value8</entry> + <entry key="key9">value9</entry> + <entry key="key10">value10</entry> + <entry key="key11">value11</entry> +</properties>