Skip to content

Commit

Permalink
use json5 config (#287)
Browse files Browse the repository at this point in the history
* add streaming json5 api to mcless

* work

* annotation based comments

* gracefully convert json config to json5

* convert array comments to json5 comments

* read with regular gson reader

* refactor annotation commenter

* use list instead of jsonpath

* comment plugin config file

* fix json -> json5 migration

* comment waila config

* only show test plugin toggle if it is enabled in the config

* don't escape backslashes on comments

* gracefully migrate plugin config json

* separate debug config

* import

(cherry picked from commit d4290ce)
  • Loading branch information
deirn committed Aug 11, 2024
1 parent 1e47e0b commit c21ce6e
Show file tree
Hide file tree
Showing 24 changed files with 1,223 additions and 101 deletions.
1 change: 1 addition & 0 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,7 @@ dependencies {
val minecraftlessImplementation by configurations

minecraftlessImplementation("com.google.code.gson:gson:2.8.9")
minecraftlessImplementation("commons-io:commons-io:2.11.0")
minecraftlessImplementation("org.jetbrains:annotations:24.1.0")

testImplementation(platform("org.junit:junit-bom:5.10.2"))
Expand Down
5 changes: 0 additions & 5 deletions platform/fabric/src/main/resources/waila_plugins.json
Original file line number Diff line number Diff line change
Expand Up @@ -33,10 +33,5 @@
"initializer": "mcp.mobius.waila.plugin.trenergy.WailaPluginTeamRebornEnergy",
"side" : "*",
"required" : ["team_reborn_energy"]
},

"waila:test" : {
"initializer" : "mcp.mobius.waila.plugin.test.WailaPluginTest",
"defaultEnabled": false
}
}
9 changes: 2 additions & 7 deletions platform/forge/src/main/resources/waila_plugins.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
"required" : ["minecraft"]
},

"waila:harvest" : {
"waila:harvest": {
"initializer": "mcp.mobius.waila.plugin.harvest.WailaPluginHarvest",
"side" : "*",
"required" : []
Expand All @@ -23,14 +23,9 @@
"required" : []
},

"waila:forge" : {
"waila:forge" : {
"initializer": "mcp.mobius.waila.plugin.forge.WailaPluginForge",
"side" : "*",
"required" : ["forge"]
},

"waila:test" : {
"initializer" : "mcp.mobius.waila.plugin.test.WailaPluginTest",
"defaultEnabled": false
}
}
5 changes: 0 additions & 5 deletions platform/quilt/src/main/resources/waila_plugins.json
Original file line number Diff line number Diff line change
Expand Up @@ -33,10 +33,5 @@
"initializer": "mcp.mobius.waila.plugin.trenergy.WailaPluginTeamRebornEnergy",
"side" : "*",
"required" : ["team_reborn_energy"]
},

"waila:test" : {
"initializer" : "mcp.mobius.waila.plugin.test.WailaPluginTest",
"defaultEnabled": false
}
}
40 changes: 40 additions & 0 deletions src/api/java/mcp/mobius/waila/api/IJsonConfig.java
Original file line number Diff line number Diff line change
@@ -1,7 +1,12 @@
package mcp.mobius.waila.api;

import java.io.File;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import java.nio.file.Path;
import java.util.List;
import java.util.function.ObjIntConsumer;
import java.util.function.Supplier;
import java.util.function.ToIntFunction;
Expand Down Expand Up @@ -79,6 +84,37 @@ default void backup() {
this.backup(null);
}

/**
* Adds comment for this value.
*
* @see Builder1#commenter(Supplier)
*/
@Target({ElementType.TYPE, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@interface Comment {

/**
* The comment.
*/
String value();

}

/**
* A custom commenter.
*/
interface Commenter {

/**
* Returns the comment for the specified path.
*
* @param path a list containing the nested path of the entry, empty list means the root object
*/
@Nullable
String getComment(List<String> path);

}

interface Builder0<T> {

Builder1<T> file(File file);
Expand All @@ -93,6 +129,10 @@ interface Builder1<T> {

Builder1<T> version(int currentVersion, ToIntFunction<T> versionGetter, ObjIntConsumer<T> versionSetter);

Builder1<T> json5();

Builder1<T> commenter(Supplier<Commenter> commenter);

Builder1<T> gson(Gson gson);

Builder1<T> factory(Supplier<T> factory);
Expand Down
10 changes: 10 additions & 0 deletions src/main/java/mcp/mobius/waila/Waila.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import mcp.mobius.waila.api.WailaConstants;
import mcp.mobius.waila.api.__internal__.IHarvestService;
import mcp.mobius.waila.config.BlacklistConfig;
import mcp.mobius.waila.config.DebugConfig;
import mcp.mobius.waila.config.WailaConfig;
import mcp.mobius.waila.gui.hud.theme.ThemeDefinition;
import mcp.mobius.waila.registry.RegistryFilter;
Expand All @@ -33,6 +34,8 @@ public abstract class Waila {
public static final IJsonConfig<WailaConfig> CONFIG = IJsonConfig.of(WailaConfig.class)
.file(WailaConstants.NAMESPACE + "/" + WailaConstants.WAILA)
.version(WailaConstants.CONFIG_VERSION, WailaConfig::getConfigVersion, WailaConfig::setConfigVersion)
.json5()
.commenter(WailaConfig.COMMENTER)
.gson(new GsonBuilder()
.setPrettyPrinting()
.registerTypeAdapter(WailaConfig.Overlay.Color.class, new WailaConfig.Overlay.Color.Adapter())
Expand All @@ -44,12 +47,19 @@ public abstract class Waila {
public static final IJsonConfig<BlacklistConfig> BLACKLIST_CONFIG = IJsonConfig.of(BlacklistConfig.class)
.file(WailaConstants.NAMESPACE + "/blacklist")
.version(BlacklistConfig.VERSION, BlacklistConfig::getConfigVersion, BlacklistConfig::setConfigVersion)
.json5()
.commenter(() -> BlacklistConfig.COMMENTER)
.gson(new GsonBuilder()
.setPrettyPrinting()
.registerTypeAdapter(BlacklistConfig.class, new BlacklistConfig.Adapter())
.create())
.build();

public static final IJsonConfig<DebugConfig> DEBUG_CONFIG = IJsonConfig.of(DebugConfig.class)
.file(WailaConstants.NAMESPACE + "/debug")
.json5()
.build();

public static ResourceLocation id(String path) {
return new ResourceLocation(WailaConstants.NAMESPACE, path);
}
Expand Down
24 changes: 10 additions & 14 deletions src/main/java/mcp/mobius/waila/config/BlacklistConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
import com.google.gson.JsonSerializer;
import mcp.mobius.waila.Waila;
import mcp.mobius.waila.api.IBlacklistConfig;
import mcp.mobius.waila.api.IJsonConfig;
import mcp.mobius.waila.api.IRegistryFilter;
import mcp.mobius.waila.util.Log;
import net.minecraft.core.Registry;
Expand All @@ -31,11 +32,20 @@ public class BlacklistConfig {
private static final String BLACKLIST_TAG = "#" + Waila.id("blacklist");

public static final int VERSION = 0;
public static final IJsonConfig.Commenter COMMENTER = p -> !p.isEmpty() ? null : """
Run `/waila reload` to apply changes server-wide.
Run `/wailac reload` to apply changes to only your client.
%s
The `%s` tag rule can not be removed"""
.formatted(IRegistryFilter.getHeader(), BLACKLIST_TAG);

public final LinkedHashSet<String> blocks = new LinkedHashSet<>();
public final LinkedHashSet<String> blockEntityTypes = new LinkedHashSet<>();
public final LinkedHashSet<String> entityTypes = new LinkedHashSet<>();

@IJsonConfig.Comment("\nThe values below are used internally by WTHIT, you SHOULD NOT modify it!")
private int configVersion = 0;
public int[] pluginHash = {0, 0, 0};

Expand Down Expand Up @@ -118,20 +128,6 @@ public static class Adapter implements JsonSerializer<BlacklistConfig>, JsonDese
public JsonElement serialize(BlacklistConfig src, Type typeOfSrc, JsonSerializationContext context) {
var object = new JsonObject();

var comments = """
Run /waila reload to apply changes server-wide.
Run /wailac reload to apply changes to only your client.
%s
The %s tag rule can not be removed"""
.formatted(IRegistryFilter.getHeader(), BLACKLIST_TAG)
.split("\n");

var commentArray = new JsonArray();
for (var line : comments) commentArray.add(line);
object.add("_comment", commentArray);

src.addBlacklistTags();

object.add("blocks", context.serialize(src.blocks));
Expand Down
10 changes: 6 additions & 4 deletions src/main/java/mcp/mobius/waila/config/ConfigEntry.java
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
import java.util.function.Function;

import com.google.common.base.Preconditions;
import com.google.gson.JsonElement;
import com.google.gson.JsonNull;
import com.google.gson.JsonPrimitive;
import mcp.mobius.waila.api.IPluginInfo;
import net.minecraft.resources.ResourceLocation;
Expand All @@ -19,7 +21,7 @@ public class ConfigEntry<T> {
public static final Type<Double> DOUBLE = new Type<>((e, d) -> e.getAsDouble(), JsonPrimitive::new);
public static final Type<String> STRING = new Type<>((e, d) -> e.getAsString(), JsonPrimitive::new);
public static final Type<Enum<? extends Enum>> ENUM = new Type<>((e, d) -> Enum.valueOf(d.getDeclaringClass(), e.getAsString()), e -> new JsonPrimitive(e.name()));
public static final Type<Path> PATH = new Type<>((e, d) -> null, e -> null);
public static final Type<Path> PATH = new Type<>((e, d) -> d, e -> JsonNull.INSTANCE);

private final IPluginInfo origin;
private final ResourceLocation id;
Expand Down Expand Up @@ -136,10 +138,10 @@ private void assertInstance(T value) {

public static class Type<T> {

public final BiFunction<JsonPrimitive, T, T> parser;
public final Function<T, JsonPrimitive> serializer;
public final BiFunction<JsonElement, T, T> parser;
public final Function<T, JsonElement> serializer;

public Type(BiFunction<JsonPrimitive, T, T> parser, Function<T, JsonPrimitive> serializer) {
public Type(BiFunction<JsonElement, T, T> parser, Function<T, JsonElement> serializer) {
this.parser = parser;
this.serializer = serializer;
}
Expand Down
11 changes: 11 additions & 0 deletions src/main/java/mcp/mobius/waila/config/DebugConfig.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package mcp.mobius.waila.config;

import mcp.mobius.waila.api.IJsonConfig;

@IJsonConfig.Comment("Debug options, restart the game to apply")
public class DebugConfig {

@IJsonConfig.Comment("Show test plugin on plugin toggle screen")
public boolean showTestPluginToggle = false;

}
48 changes: 41 additions & 7 deletions src/main/java/mcp/mobius/waila/config/JsonConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import java.nio.file.Paths;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.Set;
Expand All @@ -20,6 +21,8 @@
import com.google.gson.GsonBuilder;
import mcp.mobius.waila.Waila;
import mcp.mobius.waila.api.IJsonConfig;
import mcp.mobius.waila.config.commenter.AnnotationCommenter;
import mcp.mobius.waila.config.commenter.CommenterFactories;
import mcp.mobius.waila.mcless.config.ConfigIo;
import mcp.mobius.waila.util.CachedSupplier;
import mcp.mobius.waila.util.Log;
Expand All @@ -39,9 +42,14 @@ public class JsonConfig<T> implements IJsonConfig<T> {
private final CachedSupplier<T> getter;

@SuppressWarnings("unchecked")
JsonConfig(Path path, Type clazz, Supplier<T> factory, Gson gson, int currentVersion, ToIntFunction<T> versionGetter, ObjIntConsumer<T> versionSetter) {
JsonConfig(Path path, Type type, Supplier<T> factory, boolean json5, Supplier<Commenter> commenter, Gson gson, int currentVersion, ToIntFunction<T> versionGetter, ObjIntConsumer<T> versionSetter) {
this.path = path.toAbsolutePath();
this.io = new ConfigIo<>(LOG::warn, LOG::error, gson, clazz, factory, currentVersion, versionGetter, versionSetter);

var commenterFactories = new ArrayList<Supplier<Commenter>>();
if (type instanceof Class<?> cls) commenterFactories.add(() -> new AnnotationCommenter(cls, gson));
commenterFactories.add(commenter);

this.io = new ConfigIo<>(LOG::warn, LOG::error, json5, new CommenterFactories(commenterFactories), gson, type, factory, currentVersion, versionGetter, versionSetter);
this.getter = new CachedSupplier<>(() -> io.read(this.path));

INSTANCES.add((JsonConfig<Object>) this);
Expand Down Expand Up @@ -99,7 +107,9 @@ public void backup(@Nullable String cause) {
public static class Builder<T> implements Builder0<T>, Builder1<T> {

final Type type;
Path path;
Supplier<Path> path;
boolean json5;
Supplier<Commenter> commenter;
Gson gson;
int currentVersion;
ToIntFunction<T> versionGetter;
Expand All @@ -109,6 +119,8 @@ public static class Builder<T> implements Builder0<T>, Builder1<T> {
@SuppressWarnings("unchecked")
public Builder(Type type) {
this.type = type;
this.json5 = false;
this.commenter = () -> s -> null;
this.gson = DEFAULT_GSON;
this.currentVersion = 0;
this.versionGetter = t -> 0;
Expand All @@ -125,19 +137,29 @@ public Builder(Type type) {

@Override
public Builder1<T> file(File file) {
this.path = file.toPath();
this.path = file::toPath;
return this;
}

@Override
public Builder1<T> file(Path path) {
this.path = path;
this.path = () -> path;
return this;
}

@Override
public Builder1<T> file(String fileName) {
this.path = Waila.CONFIG_DIR.resolve(fileName + (fileName.endsWith(".json") ? "" : ".json"));
this.path = () -> {
var path = fileName;
if (json5) {
if (!path.endsWith(".json5")) path += ".json5";
} else {
if (!path.endsWith(".json")) path += ".json";
}

return Waila.CONFIG_DIR.resolve(path);
};

return this;
}

Expand All @@ -155,6 +177,18 @@ public Builder1<T> factory(Supplier<T> factory) {
return this;
}

@Override
public Builder1<T> json5() {
this.json5 = true;
return this;
}

@Override
public Builder1<T> commenter(Supplier<Commenter> commenter) {
this.commenter = commenter;
return this;
}

@Override
public Builder1<T> gson(Gson gson) {
this.gson = gson;
Expand All @@ -164,7 +198,7 @@ public Builder1<T> gson(Gson gson) {
@Override
public IJsonConfig<T> build() {
Preconditions.checkNotNull(factory, "Default value factory must not be null");
return new JsonConfig<>(path, type, factory, gson, currentVersion, versionGetter, versionSetter);
return new JsonConfig<>(path.get(), type, factory, json5, commenter, gson, currentVersion, versionGetter, versionSetter);
}

}
Expand Down
Loading

0 comments on commit c21ce6e

Please sign in to comment.