mirror of
https://github.com/lightbend/config.git
synced 2025-03-25 16:50:40 +08:00
Groundwork for the new file() url() classpath() include syntax
This patch doesn't have the parser just the implementation
This commit is contained in:
parent
cdd3e127fc
commit
3b7d99a797
@ -34,4 +34,13 @@ public interface ConfigIncludeContext {
|
||||
* null
|
||||
*/
|
||||
ConfigParseable relativeTo(String filename);
|
||||
|
||||
/**
|
||||
* Parse options to use (if you use another method to get a
|
||||
* {@link ConfigParseable} then use {@link ConfigParseable#options()}
|
||||
* instead though).
|
||||
*
|
||||
* @return the parse options
|
||||
*/
|
||||
ConfigParseOptions parseOptions();
|
||||
}
|
||||
|
@ -6,7 +6,9 @@ package com.typesafe.config;
|
||||
/**
|
||||
* Implement this interface and provide an instance to
|
||||
* {@link ConfigParseOptions#setIncluder ConfigParseOptions.setIncluder()} to
|
||||
* customize handling of {@code include} statements in config files.
|
||||
* customize handling of {@code include} statements in config files. You may
|
||||
* also want to implement {@link ConfigIncluderClasspath},
|
||||
* {@link ConfigIncluderFile}, and {@link ConfigIncluderURL}, or not.
|
||||
*/
|
||||
public interface ConfigIncluder {
|
||||
/**
|
||||
@ -30,7 +32,14 @@ public interface ConfigIncluder {
|
||||
* Parses another item to be included. The returned object typically would
|
||||
* not have substitutions resolved. You can throw a ConfigException here to
|
||||
* abort parsing, or return an empty object, but may not return null.
|
||||
*
|
||||
*
|
||||
* This method is used for a "heuristic" include statement that does not
|
||||
* specify file, URL, or classpath resource. If the include statement does
|
||||
* specify, then the same class implementing {@link ConfigIncluder} must
|
||||
* also implement {@link ConfigIncluderClasspath},
|
||||
* {@link ConfigIncluderFile}, or {@link ConfigIncluderURL} as needed, or a
|
||||
* default includer will be used.
|
||||
*
|
||||
* @param context
|
||||
* some info about the include context
|
||||
* @param what
|
||||
|
@ -0,0 +1,25 @@
|
||||
/**
|
||||
* Copyright (C) 2011-2012 Typesafe Inc. <http://typesafe.com>
|
||||
*/
|
||||
package com.typesafe.config;
|
||||
|
||||
/**
|
||||
* Implement this <em>in addition to</em> {@link ConfigIncluder} if you want to
|
||||
* support inclusion of files with the {@code include classpath("resource")}
|
||||
* syntax. If you do not implement this but do implement {@link ConfigIncluder},
|
||||
* attempts to load classpath resources will use the default includer.
|
||||
*/
|
||||
public interface ConfigIncluderClasspath {
|
||||
/**
|
||||
* Parses another item to be included. The returned object typically would
|
||||
* not have substitutions resolved. You can throw a ConfigException here to
|
||||
* abort parsing, or return an empty object, but may not return null.
|
||||
*
|
||||
* @param context
|
||||
* some info about the include context
|
||||
* @param what
|
||||
* the include statement's argument
|
||||
* @return a non-null ConfigObject
|
||||
*/
|
||||
ConfigObject includeResources(ConfigIncludeContext context, String what);
|
||||
}
|
@ -0,0 +1,27 @@
|
||||
/**
|
||||
* Copyright (C) 2011-2012 Typesafe Inc. <http://typesafe.com>
|
||||
*/
|
||||
package com.typesafe.config;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
/**
|
||||
* Implement this <em>in addition to</em> {@link ConfigIncluder} if you want to
|
||||
* support inclusion of files with the {@code include file("filename")} syntax.
|
||||
* If you do not implement this but do implement {@link ConfigIncluder},
|
||||
* attempts to load files will use the default includer.
|
||||
*/
|
||||
public interface ConfigIncluderFile {
|
||||
/**
|
||||
* Parses another item to be included. The returned object typically would
|
||||
* not have substitutions resolved. You can throw a ConfigException here to
|
||||
* abort parsing, or return an empty object, but may not return null.
|
||||
*
|
||||
* @param context
|
||||
* some info about the include context
|
||||
* @param what
|
||||
* the include statement's argument
|
||||
* @return a non-null ConfigObject
|
||||
*/
|
||||
ConfigObject includeFile(ConfigIncludeContext context, File what);
|
||||
}
|
@ -0,0 +1,27 @@
|
||||
/**
|
||||
* Copyright (C) 2011-2012 Typesafe Inc. <http://typesafe.com>
|
||||
*/
|
||||
package com.typesafe.config;
|
||||
|
||||
import java.net.URL;
|
||||
|
||||
/**
|
||||
* Implement this <em>in addition to</em> {@link ConfigIncluder} if you want to
|
||||
* support inclusion of files with the {@code include url("http://example.com")}
|
||||
* syntax. If you do not implement this but do implement {@link ConfigIncluder},
|
||||
* attempts to load URLs will use the default includer.
|
||||
*/
|
||||
public interface ConfigIncluderURL {
|
||||
/**
|
||||
* Parses another item to be included. The returned object typically would
|
||||
* not have substitutions resolved. You can throw a ConfigException here to
|
||||
* abort parsing, or return an empty object, but may not return null.
|
||||
*
|
||||
* @param context
|
||||
* some info about the include context
|
||||
* @param what
|
||||
* the include statement's argument
|
||||
* @return a non-null ConfigObject
|
||||
*/
|
||||
ConfigObject includeURL(ConfigIncludeContext context, URL what);
|
||||
}
|
@ -123,8 +123,7 @@ public final class ConfigParseOptions {
|
||||
if (this.includer == includer)
|
||||
return this;
|
||||
else
|
||||
return new ConfigParseOptions(this.syntax, this.originDescription,
|
||||
this.allowMissing,
|
||||
return new ConfigParseOptions(this.syntax, this.originDescription, this.allowMissing,
|
||||
includer, this.classLoader);
|
||||
}
|
||||
|
||||
@ -153,7 +152,7 @@ public final class ConfigParseOptions {
|
||||
/**
|
||||
* Set the class loader. If set to null,
|
||||
* <code>Thread.currentThread().getContextClassLoader()</code> will be used.
|
||||
*
|
||||
*
|
||||
* @param loader
|
||||
* a class loader or {@code null} to use thread context class
|
||||
* loader
|
||||
|
@ -77,39 +77,51 @@ public class ConfigImpl {
|
||||
return cache.getOrElseUpdate(loader, key, updater);
|
||||
}
|
||||
|
||||
|
||||
static class FileNameSource implements SimpleIncluder.NameSource {
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name, ConfigParseOptions parseOptions) {
|
||||
return Parseable.newFile(new File(name), parseOptions);
|
||||
}
|
||||
};
|
||||
|
||||
static class ClasspathNameSource implements SimpleIncluder.NameSource {
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name, ConfigParseOptions parseOptions) {
|
||||
return Parseable.newResources(name, parseOptions);
|
||||
}
|
||||
};
|
||||
|
||||
static class ClasspathNameSourceWithClass implements SimpleIncluder.NameSource {
|
||||
final private Class<?> klass;
|
||||
|
||||
public ClasspathNameSourceWithClass(Class<?> klass) {
|
||||
this.klass = klass;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name, ConfigParseOptions parseOptions) {
|
||||
return Parseable.newResources(klass, name, parseOptions);
|
||||
}
|
||||
};
|
||||
|
||||
/** For use ONLY by library internals, DO NOT TOUCH not guaranteed ABI */
|
||||
public static ConfigObject parseResourcesAnySyntax(final Class<?> klass,
|
||||
String resourceBasename, final ConfigParseOptions baseOptions) {
|
||||
NameSource source = new NameSource() {
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name) {
|
||||
return Parseable.newResources(klass, name, baseOptions);
|
||||
}
|
||||
};
|
||||
public static ConfigObject parseResourcesAnySyntax(Class<?> klass, String resourceBasename,
|
||||
ConfigParseOptions baseOptions) {
|
||||
NameSource source = new ClasspathNameSourceWithClass(klass);
|
||||
return SimpleIncluder.fromBasename(source, resourceBasename, baseOptions);
|
||||
}
|
||||
|
||||
/** For use ONLY by library internals, DO NOT TOUCH not guaranteed ABI */
|
||||
public static ConfigObject parseResourcesAnySyntax(String resourceBasename,
|
||||
final ConfigParseOptions baseOptions) {
|
||||
NameSource source = new NameSource() {
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name) {
|
||||
return Parseable.newResources(name, baseOptions);
|
||||
}
|
||||
};
|
||||
ConfigParseOptions baseOptions) {
|
||||
NameSource source = new ClasspathNameSource();
|
||||
return SimpleIncluder.fromBasename(source, resourceBasename, baseOptions);
|
||||
}
|
||||
|
||||
/** For use ONLY by library internals, DO NOT TOUCH not guaranteed ABI */
|
||||
public static ConfigObject parseFileAnySyntax(final File basename,
|
||||
final ConfigParseOptions baseOptions) {
|
||||
NameSource source = new NameSource() {
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name) {
|
||||
return Parseable.newFile(new File(name), baseOptions);
|
||||
}
|
||||
};
|
||||
public static ConfigObject parseFileAnySyntax(File basename, ConfigParseOptions baseOptions) {
|
||||
NameSource source = new FileNameSource();
|
||||
return SimpleIncluder.fromBasename(source, basename.getPath(), baseOptions);
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,14 @@
|
||||
/**
|
||||
* Copyright (C) 2011-2012 Typesafe Inc. <http://typesafe.com>
|
||||
*/
|
||||
package com.typesafe.config.impl;
|
||||
|
||||
import com.typesafe.config.ConfigIncluder;
|
||||
import com.typesafe.config.ConfigIncluderClasspath;
|
||||
import com.typesafe.config.ConfigIncluderFile;
|
||||
import com.typesafe.config.ConfigIncluderURL;
|
||||
|
||||
interface FullIncluder extends ConfigIncluder, ConfigIncluderFile, ConfigIncluderURL,
|
||||
ConfigIncluderClasspath {
|
||||
|
||||
}
|
@ -57,7 +57,10 @@ public abstract class Parseable implements ConfigParseable {
|
||||
}
|
||||
ConfigParseOptions modified = baseOptions.setSyntax(syntax);
|
||||
|
||||
// make sure the app-provided includer falls back to default
|
||||
modified = modified.appendIncluder(ConfigImpl.defaultIncluder());
|
||||
// make sure the app-provided includer is complete
|
||||
modified = modified.setIncluder(SimpleIncluder.makeFull(modified.getIncluder()));
|
||||
|
||||
return modified;
|
||||
}
|
||||
|
@ -16,7 +16,6 @@ import java.util.Stack;
|
||||
|
||||
import com.typesafe.config.ConfigException;
|
||||
import com.typesafe.config.ConfigIncludeContext;
|
||||
import com.typesafe.config.ConfigIncluder;
|
||||
import com.typesafe.config.ConfigOrigin;
|
||||
import com.typesafe.config.ConfigParseOptions;
|
||||
import com.typesafe.config.ConfigSyntax;
|
||||
@ -27,8 +26,8 @@ final class Parser {
|
||||
static AbstractConfigValue parse(Iterator<Token> tokens,
|
||||
ConfigOrigin origin, ConfigParseOptions options,
|
||||
ConfigIncludeContext includeContext) {
|
||||
ParseContext context = new ParseContext(options.getSyntax(), origin,
|
||||
tokens, options.getIncluder(), includeContext);
|
||||
ParseContext context = new ParseContext(options.getSyntax(), origin, tokens,
|
||||
SimpleIncluder.makeFull(options.getIncluder()), includeContext);
|
||||
return context.parse();
|
||||
}
|
||||
|
||||
@ -80,7 +79,7 @@ final class Parser {
|
||||
private int lineNumber;
|
||||
final private Stack<TokenWithComments> buffer;
|
||||
final private Iterator<Token> tokens;
|
||||
final private ConfigIncluder includer;
|
||||
final private FullIncluder includer;
|
||||
final private ConfigIncludeContext includeContext;
|
||||
final private ConfigSyntax flavor;
|
||||
final private ConfigOrigin baseOrigin;
|
||||
@ -90,9 +89,8 @@ final class Parser {
|
||||
// someone may think this is .properties format.
|
||||
int equalsCount;
|
||||
|
||||
ParseContext(ConfigSyntax flavor, ConfigOrigin origin,
|
||||
Iterator<Token> tokens, ConfigIncluder includer,
|
||||
ConfigIncludeContext includeContext) {
|
||||
ParseContext(ConfigSyntax flavor, ConfigOrigin origin, Iterator<Token> tokens,
|
||||
FullIncluder includer, ConfigIncludeContext includeContext) {
|
||||
lineNumber = 1;
|
||||
buffer = new Stack<TokenWithComments>();
|
||||
this.tokens = tokens;
|
||||
|
@ -4,6 +4,7 @@
|
||||
package com.typesafe.config.impl;
|
||||
|
||||
import com.typesafe.config.ConfigIncludeContext;
|
||||
import com.typesafe.config.ConfigParseOptions;
|
||||
import com.typesafe.config.ConfigParseable;
|
||||
|
||||
class SimpleIncludeContext implements ConfigIncludeContext {
|
||||
@ -14,12 +15,11 @@ class SimpleIncludeContext implements ConfigIncludeContext {
|
||||
this.parseable = parseable;
|
||||
}
|
||||
|
||||
SimpleIncludeContext() {
|
||||
this(null);
|
||||
}
|
||||
|
||||
SimpleIncludeContext withParseable(Parseable parseable) {
|
||||
return new SimpleIncludeContext(parseable);
|
||||
if (parseable == this.parseable)
|
||||
return this;
|
||||
else
|
||||
return new SimpleIncludeContext(parseable);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -29,4 +29,9 @@ class SimpleIncludeContext implements ConfigIncludeContext {
|
||||
else
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigParseOptions parseOptions() {
|
||||
return SimpleIncluder.clearForInclude(parseable.options());
|
||||
}
|
||||
}
|
||||
|
@ -3,18 +3,25 @@
|
||||
*/
|
||||
package com.typesafe.config.impl;
|
||||
|
||||
import java.io.File;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URL;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import com.typesafe.config.ConfigException;
|
||||
import com.typesafe.config.ConfigFactory;
|
||||
import com.typesafe.config.ConfigIncludeContext;
|
||||
import com.typesafe.config.ConfigIncluder;
|
||||
import com.typesafe.config.ConfigIncluderClasspath;
|
||||
import com.typesafe.config.ConfigIncluderFile;
|
||||
import com.typesafe.config.ConfigIncluderURL;
|
||||
import com.typesafe.config.ConfigObject;
|
||||
import com.typesafe.config.ConfigParseOptions;
|
||||
import com.typesafe.config.ConfigParseable;
|
||||
import com.typesafe.config.ConfigSyntax;
|
||||
|
||||
class SimpleIncluder implements ConfigIncluder {
|
||||
class SimpleIncluder implements FullIncluder {
|
||||
|
||||
private ConfigIncluder fallback;
|
||||
|
||||
@ -22,24 +29,17 @@ class SimpleIncluder implements ConfigIncluder {
|
||||
this.fallback = fallback;
|
||||
}
|
||||
|
||||
// ConfigIncludeContext does this for us on its options
|
||||
static ConfigParseOptions clearForInclude(ConfigParseOptions options) {
|
||||
// the class loader and includer are inherited, but not this other
|
||||
// stuff.
|
||||
return options.setSyntax(null).setOriginDescription(null).setAllowMissing(true);
|
||||
}
|
||||
|
||||
// this is the heuristic includer
|
||||
@Override
|
||||
public ConfigObject include(final ConfigIncludeContext context, String name) {
|
||||
NameSource source = new NameSource() {
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name) {
|
||||
ConfigParseable p = context.relativeTo(name);
|
||||
if (p == null) {
|
||||
// avoid returning null
|
||||
return Parseable.newNotFound(name, "include was not found: '" + name + "'",
|
||||
ConfigParseOptions.defaults());
|
||||
} else {
|
||||
return p;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
ConfigObject obj = fromBasename(source, name, ConfigParseOptions.defaults()
|
||||
.setAllowMissing(true));
|
||||
ConfigObject obj = includeWithoutFallback(context, name);
|
||||
|
||||
// now use the fallback includer if any and merge
|
||||
// its result.
|
||||
@ -50,6 +50,79 @@ class SimpleIncluder implements ConfigIncluder {
|
||||
}
|
||||
}
|
||||
|
||||
// the heuristic includer in static form
|
||||
static ConfigObject includeWithoutFallback(final ConfigIncludeContext context, String name) {
|
||||
// the heuristic is valid URL then URL, else relative to including file;
|
||||
// relativeTo in a file falls back to classpath inside relativeTo().
|
||||
|
||||
URL url;
|
||||
try {
|
||||
url = new URL(name);
|
||||
} catch (MalformedURLException e) {
|
||||
url = null;
|
||||
}
|
||||
|
||||
if (url != null) {
|
||||
return includeURLWithoutFallback(context, url);
|
||||
} else {
|
||||
NameSource source = new RelativeNameSource(context);
|
||||
return fromBasename(source, name, context.parseOptions());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject includeURL(ConfigIncludeContext context, URL url) {
|
||||
ConfigObject obj = includeURLWithoutFallback(context, url);
|
||||
|
||||
// now use the fallback includer if any and merge
|
||||
// its result.
|
||||
if (fallback != null && fallback instanceof ConfigIncluderURL) {
|
||||
return obj.withFallback(((ConfigIncluderURL) fallback).includeURL(context, url));
|
||||
} else {
|
||||
return obj;
|
||||
}
|
||||
}
|
||||
|
||||
static ConfigObject includeURLWithoutFallback(final ConfigIncludeContext context, URL url) {
|
||||
return ConfigFactory.parseURL(url, context.parseOptions()).root();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject includeFile(ConfigIncludeContext context, File file) {
|
||||
ConfigObject obj = includeFileWithoutFallback(context, file);
|
||||
|
||||
// now use the fallback includer if any and merge
|
||||
// its result.
|
||||
if (fallback != null && fallback instanceof ConfigIncluderFile) {
|
||||
return obj.withFallback(((ConfigIncluderFile) fallback).includeFile(context, file));
|
||||
} else {
|
||||
return obj;
|
||||
}
|
||||
}
|
||||
|
||||
static ConfigObject includeFileWithoutFallback(final ConfigIncludeContext context, File file) {
|
||||
return ConfigFactory.parseFileAnySyntax(file, context.parseOptions()).root();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject includeResources(ConfigIncludeContext context, String resource) {
|
||||
ConfigObject obj = includeResourceWithoutFallback(context, resource);
|
||||
|
||||
// now use the fallback includer if any and merge
|
||||
// its result.
|
||||
if (fallback != null && fallback instanceof ConfigIncluderClasspath) {
|
||||
return obj.withFallback(((ConfigIncluderClasspath) fallback).includeResources(context,
|
||||
resource));
|
||||
} else {
|
||||
return obj;
|
||||
}
|
||||
}
|
||||
|
||||
static ConfigObject includeResourceWithoutFallback(final ConfigIncludeContext context,
|
||||
String resource) {
|
||||
return ConfigFactory.parseResourcesAnySyntax(resource, context.parseOptions()).root();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigIncluder withFallback(ConfigIncluder fallback) {
|
||||
if (this == fallback) {
|
||||
@ -64,9 +137,29 @@ class SimpleIncluder implements ConfigIncluder {
|
||||
}
|
||||
|
||||
interface NameSource {
|
||||
ConfigParseable nameToParseable(String name);
|
||||
ConfigParseable nameToParseable(String name, ConfigParseOptions parseOptions);
|
||||
}
|
||||
|
||||
static private class RelativeNameSource implements NameSource {
|
||||
final private ConfigIncludeContext context;
|
||||
|
||||
RelativeNameSource(ConfigIncludeContext context) {
|
||||
this.context = context;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigParseable nameToParseable(String name, ConfigParseOptions options) {
|
||||
ConfigParseable p = context.relativeTo(name);
|
||||
if (p == null) {
|
||||
// avoid returning null
|
||||
return Parseable
|
||||
.newNotFound(name, "include was not found: '" + name + "'", options);
|
||||
} else {
|
||||
return p;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// this function is a little tricky because there are three places we're
|
||||
// trying to use it; for 'include "basename"' in a .conf file, for
|
||||
// loading app.{conf,json,properties} from classpath, and for
|
||||
@ -74,13 +167,13 @@ class SimpleIncluder implements ConfigIncluder {
|
||||
static ConfigObject fromBasename(NameSource source, String name, ConfigParseOptions options) {
|
||||
ConfigObject obj;
|
||||
if (name.endsWith(".conf") || name.endsWith(".json") || name.endsWith(".properties")) {
|
||||
ConfigParseable p = source.nameToParseable(name);
|
||||
ConfigParseable p = source.nameToParseable(name, options);
|
||||
|
||||
obj = p.parse(p.options().setAllowMissing(options.getAllowMissing()));
|
||||
} else {
|
||||
ConfigParseable confHandle = source.nameToParseable(name + ".conf");
|
||||
ConfigParseable jsonHandle = source.nameToParseable(name + ".json");
|
||||
ConfigParseable propsHandle = source.nameToParseable(name + ".properties");
|
||||
ConfigParseable confHandle = source.nameToParseable(name + ".conf", options);
|
||||
ConfigParseable jsonHandle = source.nameToParseable(name + ".json", options);
|
||||
ConfigParseable propsHandle = source.nameToParseable(name + ".properties", options);
|
||||
boolean gotSomething = false;
|
||||
List<String> failMessages = new ArrayList<String>();
|
||||
|
||||
@ -140,4 +233,57 @@ class SimpleIncluder implements ConfigIncluder {
|
||||
|
||||
return obj;
|
||||
}
|
||||
|
||||
// the Proxy is a proxy for an application-provided includer that uses our
|
||||
// default implementations when the application-provided includer doesn't
|
||||
// have an implementation.
|
||||
static private class Proxy implements FullIncluder {
|
||||
final ConfigIncluder delegate;
|
||||
|
||||
Proxy(ConfigIncluder delegate) {
|
||||
this.delegate = delegate;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigIncluder withFallback(ConfigIncluder fallback) {
|
||||
// we never fall back
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject include(ConfigIncludeContext context, String what) {
|
||||
return delegate.include(context, what);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject includeResources(ConfigIncludeContext context, String what) {
|
||||
if (delegate instanceof ConfigIncluderClasspath)
|
||||
return ((ConfigIncluderClasspath) delegate).includeResources(context, what);
|
||||
else
|
||||
return includeResourceWithoutFallback(context, what);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject includeURL(ConfigIncludeContext context, URL what) {
|
||||
if (delegate instanceof ConfigIncluderURL)
|
||||
return ((ConfigIncluderURL) delegate).includeURL(context, what);
|
||||
else
|
||||
return includeURLWithoutFallback(context, what);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConfigObject includeFile(ConfigIncludeContext context, File what) {
|
||||
if (delegate instanceof ConfigIncluderFile)
|
||||
return ((ConfigIncluderFile) delegate).includeFile(context, what);
|
||||
else
|
||||
return includeFileWithoutFallback(context, what);
|
||||
}
|
||||
}
|
||||
|
||||
static FullIncluder makeFull(ConfigIncluder includer) {
|
||||
if (includer instanceof FullIncluder)
|
||||
return (FullIncluder) includer;
|
||||
else
|
||||
return new Proxy(includer);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user