Matthias Hanisch created CONFIGURATION-833:
----------------------------------------------

             Summary: PropertiesConfiguration: Possibility to distinguish 
between "serious" and non-serious exceptions for optional configurations
                 Key: CONFIGURATION-833
                 URL: https://issues.apache.org/jira/browse/CONFIGURATION-833
             Project: Commons Configuration
          Issue Type: Improvement
            Reporter: Matthias Hanisch


With Properties files as configuration sources there not so much scenarios 
where exceptions can be raised:
 # Properties File itself cannot be found
 # Properties File is invalid, e.g. contains "invalidValue=\uZZZZ"
 # Properties File contains an "include" but the included file cannot be found

If the PropertiesConfiguration is marked as optional all errors are ignored and 
the Configuration is silently not be considered.

In our case we would like to have scenarios 2 and 3 considered as serious 
errors where the whole logic should fail independent if the configuration is 
optional or not.

While looking at the code it seems that all exceptions are transformed to 
ConfigurationExceptions and then are ignored if the configuration is optional.

It would be nice to have a possiblity to decide from application point of view 
the severity of the error and based on that having different logic, e.g. let 
the whole thing fail.

Here is some test code that illustrates the problem:

Test Class;

 
{code:java}
package commons.configuration.issues;

import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;

import java.io.File;

import org.apache.commons.configuration2.CombinedConfiguration;
import 
org.apache.commons.configuration2.builder.combined.CombinedConfigurationBuilder;
import org.apache.commons.configuration2.builder.fluent.Parameters;
import org.apache.commons.configuration2.ex.ConfigurationException;
import org.apache.commons.configuration2.ex.ConfigurationRuntimeException;
import org.junit.Test;

public class VariousErrorsAllIgnoredWithOptional {
        @Test
        public void nonOptionalIncludeNotFound() {
                CombinedConfigurationBuilder builder = new 
CombinedConfigurationBuilder()
                                .configure(new 
Parameters().fileBased().setFile(new File(
                                                
"src/test/resources/commons-configuration-issues/error-handling-include-not-found.xml")));
                /*
                 * Non optional leads always to an error
                 */
                System.setProperty("propertiesOptional", "false");
                assertThatThrownBy(() -> 
builder.getConfiguration()).isInstanceOf(ConfigurationException.class)
                                .hasMessage("Cannot resolve include file 
not_exist.properties");
        }

        @Test
        public void optionalIncludeNotFound() throws ConfigurationException {
                CombinedConfigurationBuilder builder = new 
CombinedConfigurationBuilder()
                                .configure(new 
Parameters().fileBased().setFile(new File(
                                                
"src/test/resources/commons-configuration-issues/error-handling-include-not-found.xml")));
                System.setProperty("propertiesOptional", "true");

                /*
                 * If optional then a non-working include is ignored. This is 
not desired.
                 * Would be nice to configure that as serious problem that 
leads to a general error independent of optional.
                 */
                assertThat(builder.getConfiguration()).isNotNull();
        }

        @Test
        public void nonOptionalPropertyNotFound() {
                CombinedConfigurationBuilder builder = new 
CombinedConfigurationBuilder()
                                .configure(new 
Parameters().fileBased().setFile(new File(
                                                
"src/test/resources/commons-configuration-issues/error-handling-property-not-found.xml")));
                /*
                 * Non optional leads always to an error
                 */
                System.setProperty("propertiesOptional", "false");
                assertThatThrownBy(() -> 
builder.getConfiguration()).isInstanceOf(ConfigurationException.class)
                                .hasMessageContainingAll("Could not locate", 
"not-exist.properties");
        }

        @Test
        public void optionalPropertyNotFound() throws ConfigurationException {
                CombinedConfigurationBuilder builder = new 
CombinedConfigurationBuilder()
                                .configure(new 
Parameters().fileBased().setFile(new File(
                                                
"src/test/resources/commons-configuration-issues/error-handling-properties-file-not-found.xml")));

                /*
                 * If optional then a non-working include is ignored. This is 
ok.
                 */
                System.setProperty("propertiesOptional", "true");
                assertThat(builder.getConfiguration()).isNotNull();
        }

        @Test
        public void nonOptionalInvalidPropertiesFile() {
                CombinedConfigurationBuilder builder = new 
CombinedConfigurationBuilder()
                                .configure(new 
Parameters().fileBased().setFile(new File(
                                                
"src/test/resources/commons-configuration-issues/error-handling-invalid-properties-file.xml")));
                /*
                 * Non optional leads always to an error
                 */
                System.setProperty("propertiesOptional", "false");
                assertThatThrownBy(() -> 
builder.getConfiguration()).isInstanceOf(ConfigurationException.class).cause().isInstanceOf(ConfigurationRuntimeException.class)
                                .hasMessage("Unable to parse unicode value: 
ZZZZ");
        }

        @Test
        public void optionalInvalidPropertiesFile() throws 
ConfigurationException {
                CombinedConfigurationBuilder builder = new 
CombinedConfigurationBuilder()
                                .configure(new 
Parameters().fileBased().setFile(new File(
                                                
"src/test/resources/commons-configuration-issues/error-handling-invalid-properties-file.xml")));

                /*
                 * If optional then an invalid property file is ignored. This 
is not desired.
                 * Would be nice to configure that as serious problem that 
leads to a general error independent of optional.
                 */
                System.setProperty("propertiesOptional", "true");
                CombinedConfiguration configuration = 
builder.getConfiguration();
                // At least all keys are consistently not set.
                
assertThat(configuration.getString("valueBeforeInvalid")).isNull();
                assertThat(configuration.getString("invalidValue")).isNull();
                
assertThat(configuration.getString("valueAfterInvalid")).isNull();
        }
}
{code}
error-handling-include-not-found.xml:
 
 
{code:java}
<configuration>
        <properties basePath="src/test/resources/commons-configuration-issues"
                fileName="error-handling-include-not-found.properties" 
config-optional="${sys:propertiesOptional}"/>
</configuration>{code}
error-handling-include-not-found.properties:

 
{code:java}
include = not_exist.properties
{code}
error-handling-properties-file-not-found.xml

 

 
{code:java}
<configuration>
        <properties basePath="src/test/resources/commons-configuration-issues"
                fileName="not-exist.properties" 
config-optional="${sys:propertiesOptional}"/>
</configuration>
{code}
error-handling-invalid-properties-file-not-found.xml

 

 
{code:java}
<configuration>
        <properties basePath="src/test/resources/commons-configuration-issues"
                fileName="not-exist.properties" 
config-optional="${sys:propertiesOptional}"/>
</configuration>{code}
error-handling-invalid-properties-file-not-found.properties
{code:java}
valueBeforeInvalid=1
invalidValue=\uZZZZ
valueAfterInvalid=2
{code}
 

 

 

 



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to