Skip to content

Commit

Permalink
Merge pull request #11 from tvd12/version-1.1.3
Browse files Browse the repository at this point in the history
Version 1.1.3
  • Loading branch information
tvd12 committed Oct 30, 2021
2 parents de79466 + dd8f3f2 commit 6a5994a
Show file tree
Hide file tree
Showing 12 changed files with 337 additions and 33 deletions.
6 changes: 3 additions & 3 deletions pom.xml
Expand Up @@ -3,7 +3,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>com.tvd12</groupId>
<artifactId>properties-file</artifactId>
<version>1.1.2</version>
<version>1.1.3</version>

<name>properties-file</name>
<url>http://www.tvd12.com/java/projects/properties-file</url>
Expand All @@ -13,14 +13,14 @@

<organization>
<name>Young Monkeys</name>
<url>http://www.tvd12.com</url>
<url>https://youngmonkeys.org/</url>
</organization>

<properties>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<lombok.version>1.18.20</lombok.version>
<test.util.version>1.1.1</test.util.version>
<test.util.version>1.1.2</test.util.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.build.timestamp.format>yyyy-MM-dd'T'HH:mm:ss</maven.build.timestamp.format>
</properties>
Expand Down
Expand Up @@ -56,8 +56,11 @@ public SimpleValueConverter() {
public <T> T convert(Object value, Class<T> outType) {
if(value == null)
return null;
if(transformers.containsKey(outType))
return (T) transformers.get(outType).transform(value);
Transformer transformer = transformers.get(outType);
if(transformer != null)
return (T) transformer.transform(value);
if(outType.isEnum())
return (T) Enum.valueOf((Class<Enum>)outType, value.toString());
return (T)value;
}

Expand Down
44 changes: 32 additions & 12 deletions src/main/java/com/tvd12/properties/file/reader/FileReader.java
@@ -1,6 +1,7 @@
package com.tvd12.properties.file.reader;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collection;
Expand Down Expand Up @@ -31,10 +32,14 @@ default Properties read(Class<?> context, String filePath) {
* @return properties object
*/
default Properties read(ClassLoader classLoader, String filePath) {
return loadInputStream(
InputStreamUtil.getInputStream(classLoader, filePath),
FileUtil.getFileExtension(filePath)
);
try (InputStream inputStream = InputStreamUtil.getInputStream(classLoader, filePath)) {
return loadInputStreamOrThrows(
inputStream,
FileUtil.getFileExtension(filePath)
);
} catch (IOException e) {
return new Properties();
}
}

/**
Expand Down Expand Up @@ -123,6 +128,18 @@ default Properties loadInputStream(InputStream inputStream) {
*/
Properties loadInputStream(InputStream inputStream, String contentType);

/**
* Load an input stream and read properties
*
* @param inputStream the input stream
* @param contentType the content type
* @return properties the properties
*/
default Properties loadInputStreamOrThrows(
InputStream inputStream, String contentType) throws IOException {
return loadInputStream(inputStream, contentType);
}

/**
* Read properties files
*
Expand Down Expand Up @@ -153,15 +170,18 @@ default List<Properties> loadInputStreams(Collection<InputStream> inputStreams)
* @return properties object
*/
default Properties read(File file) {
InputStream inputStream = InputStreamUtil.getInputStreamByAbsolutePath(file);
Properties properties = new Properties();
if(inputStream != null) {
properties.putAll(loadInputStream(
inputStream,
FileUtil.getFileExtension(file.getPath())
));
try(InputStream inputStream = InputStreamUtil.getInputStreamByAbsolutePath(file)) {
if(inputStream != null) {
return loadInputStreamOrThrows(
inputStream,
FileUtil.getFileExtension(file.getPath())
);
}
}
return properties;
catch (IOException e) {
// do nothing
}
return new Properties();
}

/**
Expand Down
Expand Up @@ -43,6 +43,7 @@ public abstract class ClassStruct {
*
* @param clazz java class
* @param mappingLevel the mapping level
* @param propertyAnnotations the properties annotation filter
*/
public ClassStruct(
Class<?> clazz,
Expand Down
Expand Up @@ -24,6 +24,7 @@ public class ClassWrapper extends ClassStruct {
*
* @param clazz java class
* @param mappingLevel the mapping level
* @param propertyAnnotations the properties annotation filter
*/
public ClassWrapper(
Class<?> clazz,
Expand Down
Expand Up @@ -5,6 +5,10 @@
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;

import com.tvd12.properties.file.constant.Constants;
import com.tvd12.properties.file.exception.PropertiesFileException;
Expand All @@ -25,7 +29,7 @@ public static InputStream getInputStream(
ClassLoader classLoader, String filePath) {
InputStream inputStream = getResourceAsStream(classLoader, filePath);
if(inputStream == null)
inputStream = getResourceAsStream(classLoader, "/" + filePath);
inputStream = getResourceAsStream(classLoader, "/" + filePath);
if(inputStream == null)
inputStream = getInputStreamByAbsolutePath(filePath);
if(inputStream == null)
Expand All @@ -48,9 +52,81 @@ private static InputStream getResourceAsStream(ClassLoader classLoader,
InputStream ip = acceptClassLoader.getResourceAsStream(filePath);
if(ip == null)
ip = ClassLoader.getSystemResourceAsStream(filePath);
if(ip == null)
ip = getResourceAsStreamInOthers(acceptClassLoader, filePath);
return ip;
}

/**
* Get the resource input stream from other jar files
*
* @param classLoader the class loader
* @param resource the resource to get the stream
* @return the input stream or null
*/
private static InputStream getResourceAsStreamInOthers(ClassLoader classLoader,
String resource) {
List<URL> resourcesURLs = new ArrayList<>();
try {
addResourceURLs(resourcesURLs, () -> classLoader.getResources(resource));
addResourceURLs(resourcesURLs, () -> ClassLoader.getSystemResources(resource));
addResourceURL(resourcesURLs, classLoader.getResource(resource));
addResourceURL(resourcesURLs, ClassLoader.getSystemResource(resource));
}
catch (Exception e) {
// do nothing
}
try {
return resourcesURLs.isEmpty() ? null : resourcesURLs.get(0).openStream();
} catch (IOException e) {
return null;
}
}

/**
*
* Add resource URLs
*
* @param resourcesURLs the resource URLs output
* @param supplier the resource URLs suppliers
*/
private static void addResourceURLs(List<URL> resourcesURLs, URLsSupplier supplier) {
try {
Enumeration<URL> urls = supplier.get();
addResourceURLs(resourcesURLs, urls);
}
catch (Exception e) {
// do nothing
}
}

/**
*
* Add resource URLs
*
* @param resourcesURLs the resource URLs output
* @param urls the resource URLs to add
*/
private static void addResourceURLs(List<URL> resourceURLs, Enumeration<URL> urls) {
if(urls != null) {
while(urls.hasMoreElements()) {
resourceURLs.add(urls.nextElement());
}
}
}

/**
*
* Add resource URLs
*
* @param resourcesURLs the resource URLs output
* @param url the resource URL to add
*/
private static void addResourceURL(List<URL> resourcesURLs, URL url) {
if(url != null)
resourcesURLs.add(url);
}

/**
* Get a input stream from a file if it exists and be readable
*
Expand Down Expand Up @@ -149,4 +225,8 @@ else if(b == ':') {
}
return contenType;
}

private static interface URLsSupplier {
public Enumeration<URL> get() throws IOException;
}
}
10 changes: 5 additions & 5 deletions src/main/java/com/tvd12/properties/file/util/PropertiesUtil.java
Expand Up @@ -100,8 +100,8 @@ public static Properties getPropertiesByPrefix(Map properties, String prefix) {
* password=test password
* )
*
* @param properties
* @return
* @param properties the input properties
* @return the filtered properties
*/
@SuppressWarnings("rawtypes")
public static Map<String, Properties> getPropertiesMap(Map properties) {
Expand All @@ -125,10 +125,10 @@ public static Map<String, Properties> getPropertiesMap(Map properties) {
* test_datasource.username=test username
* test_datasource.password=test password
* )
* has first property keys main_datasource and test_datasource
* has first property keys are main_datasource and test_datasource
*
* @param properties
* @return
* @param properties the input properties
* @return the first key set
*/
@SuppressWarnings("rawtypes")
public static Set<String> getFirstPropertyKeys(Map properties) {
Expand Down
14 changes: 4 additions & 10 deletions src/main/java/com/tvd12/properties/file/writer/BaseFileWriter.java
Expand Up @@ -43,10 +43,9 @@ public void write(Properties properties, String filePath) {
*/
@Override
public void write(Properties properties, File file) {
try {
try(ByteArrayOutputStream out = write(properties)) {
if(!file.exists())
file.createNewFile();
ByteArrayOutputStream out = write(properties);
byte[] bytes = encode(out);
writeBytes0(file, bytes);
}
Expand Down Expand Up @@ -85,14 +84,9 @@ protected FileOutputStream newFileOutputStream(File file) throws FileNotFoundExc
* @param out a ByteArrayOutputStream object
* @return encoded byte array
*/
protected byte[] encode(ByteArrayOutputStream out) throws IOException {
try {
byte[] bytes = out.toByteArray();
return bytes;
}
finally {
out.close();
}
protected byte[] encode(ByteArrayOutputStream out) {
byte[] bytes = out.toByteArray();
return bytes;
}

}
@@ -0,0 +1,22 @@
package com.monkey.properties.file.testing;

import java.io.Closeable;
import java.io.IOException;

public class AutoCloseTest {

private static class InternalClose implements Closeable {
@Override
public void close() throws IOException {
System.out.println("I'm closed");
}
}

public static void main(String[] args) {
try(InternalClose close = new InternalClose()) {
System.out.println(close);
} catch (IOException e) {
e.printStackTrace();
}
}
}
@@ -0,0 +1,76 @@
package com.monkey.properties.file.testing;

import static org.mockito.Mockito.doThrow;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;

import org.testng.annotations.Test;

import com.tvd12.properties.file.reader.FileReader;
import com.tvd12.test.assertion.Asserts;

import lombok.AllArgsConstructor;

public class FileReaderTest {

private static final Properties PROPERTIES = new Properties();

@Test
public void readByClassLoaderAndFileCloseFailed() throws Exception {
// given
InternalFileReader sut = new InternalFileReader(false);

ClassLoader classLoader = mock(ClassLoader.class);
String file = "config.properties";

InputStream inputStream = mock(InputStream.class);
doThrow(new IOException("just test")).when(inputStream).close();
when(classLoader.getResourceAsStream(file)).thenReturn(inputStream);

Properties actual = sut.read(classLoader, file);

// then
Asserts.assertEmpty(actual);
verify(classLoader, times(1)).getResourceAsStream(file);
}

@Test
public void readFailed() throws Exception {
// given
InternalFileReader sut = new InternalFileReader(true);

File file = new File("src/test/resources/application.yaml");

Properties actual = sut.read(file);

// then
Asserts.assertEmpty(actual);
}

@AllArgsConstructor
private static class InternalFileReader implements FileReader {

private final boolean exception;

@Override
public Properties loadInputStream(
InputStream inputStream, String contentType) {
return PROPERTIES;
}

@Override
public Properties loadInputStreamOrThrows(
InputStream inputStream, String contentType) throws IOException {
if(exception)
throw new IOException("just test");
return PROPERTIES;
}
}
}

0 comments on commit 6a5994a

Please sign in to comment.