add a Config.isResolved method

Now that partial resolution is allowed, this may be useful
for people to check after they do a partial resolve.
This commit is contained in:
Havoc Pennington 2014-01-03 10:27:44 -05:00
parent 8c0afc58d9
commit d7287c9e16
3 changed files with 34 additions and 1 deletions

View File

@ -168,10 +168,22 @@ public interface Config extends ConfigMergeable {
*
* @param options
* resolve options
* @return the resolved <code>Config</code>
* @return the resolved <code>Config</code> (may be only partially resolved if options are set to allow unresolved)
*/
Config resolve(ConfigResolveOptions options);
/**
* Checks whether the config is completely resolved. After a successful call to
* {@link Config#resolve()} it will be completely resolved, but after calling
* {@link Config#resolve(ConfigResolveOptions)} with <code>allowUnresolved</code> set
* in the options, it may or may not be completely resolved. A newly-loaded config
* may or may not be completely resolved depending on whether there were substitutions
* present in the file.
*
* @return true if there are no unresolved substitutions remaining in this configuration.
*/
boolean isResolved();
/**
* Validates this config against a reference config, throwing an exception
* if it is invalid. The purpose of this method is to "fail early" with a

View File

@ -815,6 +815,11 @@ final class SimpleConfig implements Config, MergeableValue, Serializable {
}
}
@Override
public boolean isResolved() {
return root().resolveStatus() == ResolveStatus.RESOLVED;
}
@Override
public void checkValid(Config reference, String... restrictToPaths) {
SimpleConfig ref = (SimpleConfig) reference;

View File

@ -1104,10 +1104,23 @@ class ConfigTest extends TestUtils {
}
}
@Test
def isResolvedWorks() {
val resolved = ConfigFactory.parseString("foo = 1")
assertTrue("config with no substitutions starts as resolved", resolved.isResolved)
val unresolved = ConfigFactory.parseString("foo = ${a}, a=42")
assertFalse("config with substitutions starts as not resolved", unresolved.isResolved)
val resolved2 = unresolved.resolve()
assertTrue("after resolution, config is now resolved", resolved2.isResolved)
}
@Test
def allowUnresolvedDoesAllowUnresolved() {
val values = ConfigFactory.parseString("{ foo = 1, bar = 2, m = 3, n = 4}")
assertTrue("config with no substitutions starts as resolved", values.isResolved)
val unresolved = ConfigFactory.parseString("a = ${foo}, b = ${bar}, c { x = ${m}, y = ${n} }, alwaysResolveable=${alwaysValue}, alwaysValue=42")
assertFalse("config with substitutions starts as not resolved", unresolved.isResolved)
// resolve() by default throws with unresolveable substs
intercept[ConfigException.UnresolvedSubstitution] {
unresolved.resolve(ConfigResolveOptions.defaults())
@ -1123,10 +1136,13 @@ class ConfigTest extends TestUtils {
for (k <- Seq("a", "b", "c.x", "c.y")) {
intercept[ConfigException.NotResolved] { allowedUnresolved.getInt(k) }
}
// and the partially-resolved thing is not resolved
assertFalse("partially-resolved object is not resolved", allowedUnresolved.isResolved)
// and given the values for the resolve, we should be able to
val resolved = allowedUnresolved.withFallback(values).resolve()
for (kv <- Seq("a" -> 1, "b" -> 2, "c.x" -> 3, "c.y" -> 4)) {
assertEquals(kv._2, resolved.getInt(kv._1))
}
assertTrue("fully resolved object is resolved", resolved.isResolved)
}
}