diff --git a/mod-fabric/src/eu/e99/pixelchat/fabric/Config.java b/mod-fabric/src/eu/e99/pixelchat/fabric/Config.java new file mode 100644 index 0000000..a674d7b --- /dev/null +++ b/mod-fabric/src/eu/e99/pixelchat/fabric/Config.java @@ -0,0 +1,11 @@ +package eu.e99.pixelchat.fabric; + +import com.google.gson.annotations.SerializedName; + +public class Config { + + @SerializedName("image_hosts") + public String[] imageHosts = new String[]{ + "https://pc.1e99.eu" + }; +} diff --git a/mod-fabric/src/eu/e99/pixelchat/fabric/PixelChat.java b/mod-fabric/src/eu/e99/pixelchat/fabric/PixelChat.java index 3b31f12..0292c04 100644 --- a/mod-fabric/src/eu/e99/pixelchat/fabric/PixelChat.java +++ b/mod-fabric/src/eu/e99/pixelchat/fabric/PixelChat.java @@ -1,13 +1,18 @@ package eu.e99.pixelchat.fabric; -import eu.e99.pixelchat.fabric.image.ImageUploader; +import com.google.gson.Gson; +import com.google.gson.GsonBuilder; import eu.e99.pixelchat.fabric.image.ImageUploads; -import eu.e99.pixelchat.fabric.image.PixelChatUploader; import net.fabricmc.api.ClientModInitializer; +import net.fabricmc.loader.api.FabricLoader; import net.minecraft.client.MinecraftClient; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Path; + public class PixelChat implements ClientModInitializer { public static final String NAMESPACE = "pixelchat"; @@ -16,12 +21,38 @@ public class PixelChat implements ClientModInitializer { @Override public void onInitializeClient() { + Config config = this.loadConfig(); + UPLOADS = new ImageUploads( MinecraftClient.getInstance(), - new ImageUploader[]{ - new PixelChatUploader("https://pc.1e99.eu"), - new PixelChatUploader("http://localhost:3000") - } + config.imageHosts ); } + + private Config loadConfig() { + try { + Gson gson = new GsonBuilder() + .setPrettyPrinting() + .create(); + + FabricLoader loader = FabricLoader.getInstance(); + Path path = loader.getConfigDir(); + path = path.resolve("pixelchat.json"); + + if (Files.exists(path)) { + String string = Files.readString(path); + return gson.fromJson(string, Config.class); + } + + + Config config = new Config(); + String string = gson.toJson(config); + Files.writeString(path, string); + + return config; + } catch (IOException e) { + LOGGER.error("Failed to read config, defaulting to default config", e); + return new Config(); + } + } } diff --git a/mod-fabric/src/eu/e99/pixelchat/fabric/StringList.java b/mod-fabric/src/eu/e99/pixelchat/fabric/StringList.java deleted file mode 100644 index fadba8a..0000000 --- a/mod-fabric/src/eu/e99/pixelchat/fabric/StringList.java +++ /dev/null @@ -1,55 +0,0 @@ -package eu.e99.pixelchat.fabric; - -import java.util.ArrayList; -import java.util.List; - -/** - * A StringList is a list of strings encoded like this: [string1,string2,string3] - * Strings can contain any character except '[', ']' and ',' - */ -public class StringList { - - public static List fromString(String str) { - List tags = new ArrayList<>(); - char[] chars = str.toCharArray(); - int i = 0; - - if (chars[i++] != '[') { - return null; - } - - while (i < chars.length && chars[i] != ']') { - StringBuilder builder = new StringBuilder(); - while (i < chars.length && chars[i] != ',' && chars[i] != ']') { - builder.append(chars[i]); - i++; - } - - tags.add(builder.toString()); - i++; - } - - for (String tag : tags) { - System.out.printf("%s%n", tag); - } - - return tags; - } - - public static String toString(List tags) { - StringBuilder builder = new StringBuilder(); - builder.append('['); - - int length = tags.size(); - for (int i = 0; i < length; i++) { - builder.append(tags.get(i)); - - if (i < length - 1) { - builder.append(','); - } - } - - builder.append(']'); - return builder.toString(); - } -} diff --git a/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploader.java b/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploader.java deleted file mode 100644 index d0e386d..0000000 --- a/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploader.java +++ /dev/null @@ -1,11 +0,0 @@ -package eu.e99.pixelchat.fabric.image; - -import java.nio.file.Path; - -public interface ImageUploader { - - /** - * @return An URL to a downloadable PNG file - */ - String upload(Path path) throws Throwable; -} diff --git a/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploads.java b/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploads.java index be6a7c9..c5c41ec 100644 --- a/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploads.java +++ b/mod-fabric/src/eu/e99/pixelchat/fabric/image/ImageUploads.java @@ -7,17 +7,24 @@ import net.minecraft.client.gui.hud.ClientBossBar; import net.minecraft.entity.boss.BossBar; import net.minecraft.text.Text; +import java.net.URI; +import java.net.http.HttpClient; +import java.net.http.HttpRequest; +import java.net.http.HttpResponse; import java.nio.file.Path; +import java.util.List; import java.util.UUID; public class ImageUploads { - private final MinecraftClient client; - private final ImageUploader[] uploaders; + private final MinecraftClient minecraft; + private final String[] hosts; + private final HttpClient client; - public ImageUploads(MinecraftClient client, ImageUploader[] uploaders) { - this.client = client; - this.uploaders = uploaders; + public ImageUploads(MinecraftClient minecraft, String[] hosts) { + this.minecraft = minecraft; + this.hosts = hosts; + this.client = HttpClient.newHttpClient(); } public void uploadImage(Path path) { @@ -25,7 +32,7 @@ public class ImageUploads { } private void innerUploadImage(Path path) { - BossBars bossBars = (BossBars) client.inGameHud.getBossBarHud(); + BossBars bossBars = (BossBars) minecraft.inGameHud.getBossBarHud(); ClientBossBar bossBar = new ClientBossBar( UUID.randomUUID(), Text.translatable("pixelchat.uploading"), @@ -37,12 +44,12 @@ public class ImageUploads { false ); - this.client.send(() -> bossBars.add(bossBar.getUuid(), bossBar)); + this.minecraft.send(() -> bossBars.add(bossBar.getUuid(), bossBar)); String url = null; - for (ImageUploader uploader : this.uploaders) { + for (String host : this.hosts) { try { - url = uploader.upload(path); + url = this.upload(host, path); break; } catch (Throwable e) { PixelChat.LOGGER.warn("Failed to upload", e); @@ -51,7 +58,7 @@ public class ImageUploads { // IntelliJ complains otherwise String finalUrl = url; - this.client.send(() -> { + this.minecraft.send(() -> { if (finalUrl == null) { PixelChat.LOGGER.error("No uploader succeeded"); bossBar.setName(Text.translatable("pixelchat.upload_failed")); @@ -65,12 +72,12 @@ public class ImageUploads { bossBar.setColor(BossBar.Color.GREEN); // TODO: Are we actually playing? - if (this.client.player == null) { + if (this.minecraft.player == null) { return; } - this.client.inGameHud.getChatHud().addToMessageHistory(finalUrl); - this.client.player.networkHandler.sendChatMessage(finalUrl); + this.minecraft.inGameHud.getChatHud().addToMessageHistory(finalUrl); + this.minecraft.player.networkHandler.sendChatMessage(finalUrl); }); try { @@ -78,6 +85,29 @@ public class ImageUploads { } catch (InterruptedException ignored) { } - this.client.send(() -> bossBars.remove(bossBar.getUuid())); + this.minecraft.send(() -> bossBars.remove(bossBar.getUuid())); + } + + private String upload(String host, Path path) throws Throwable { + String uri = url(host, ""); + HttpRequest req = HttpRequest.newBuilder() + .POST(HttpRequest.BodyPublishers.ofFile(path)) + .uri(URI.create(uri)) + .build(); + + HttpResponse res = this.client.send( + req, + HttpResponse.BodyHandlers.ofString() + ); + if (res.statusCode() != 201) { + throw new RuntimeException(String.format("Failed to upload, expected status 201, got %d", res.statusCode())); + } + + String id = res.body(); + return url(host, id); + } + + private static String url(String host, String path) { + return String.format("%s/%s", host, path); } } diff --git a/mod-fabric/src/eu/e99/pixelchat/fabric/image/PixelChatUploader.java b/mod-fabric/src/eu/e99/pixelchat/fabric/image/PixelChatUploader.java deleted file mode 100644 index a0a78cd..0000000 --- a/mod-fabric/src/eu/e99/pixelchat/fabric/image/PixelChatUploader.java +++ /dev/null @@ -1,45 +0,0 @@ -package eu.e99.pixelchat.fabric.image; - -import java.net.URI; -import java.net.http.HttpClient; -import java.net.http.HttpRequest; -import java.net.http.HttpResponse; -import java.nio.file.Path; - -public class PixelChatUploader implements ImageUploader { - - private final HttpClient client; - private final String host; - - /** - * @param host A valid URI to the server. Must not end with a slash. Valid examples are: {@code https://pc.1e99.eu} or {@code http://localhost:3000}. - */ - public PixelChatUploader(String host) { - this.client = HttpClient.newHttpClient(); - this.host = host; - } - - @Override - public String upload(Path path) throws Throwable { - String uri = this.url(""); - HttpRequest req = HttpRequest.newBuilder() - .POST(HttpRequest.BodyPublishers.ofFile(path)) - .uri(URI.create(uri)) - .build(); - - HttpResponse res = this.client.send( - req, - HttpResponse.BodyHandlers.ofString() - ); - if (res.statusCode() != 201) { - throw new RuntimeException(String.format("Failed to upload, expected status 201, got %d", res.statusCode())); - } - - String id = res.body(); - return this.url(id); - } - - private String url(String path) { - return String.format("%s/%s", this.host, path); - } -}