From 665bc5141b9820b053dcbaa377d0636bd358babc Mon Sep 17 00:00:00 2001 From: Niels NTG Date: Fri, 16 Dec 2022 22:11:24 +0100 Subject: [PATCH] Add GET /biomes endpoint --- README.md | 1 + .../gdmc/httpinterfacemod/GdmcHttpServer.java | 1 + .../handlers/BiomesHandler.java | 102 ++++++++++++++++++ 3 files changed, 104 insertions(+) create mode 100644 src/main/java/com/gdmc/httpinterfacemod/handlers/BiomesHandler.java diff --git a/README.md b/README.md index 9909873..a807f57 100644 --- a/README.md +++ b/README.md @@ -20,6 +20,7 @@ The current endpoints of the interface are GET,PUT /blocks Modify blocks in the world POST /command Run Minecraft commands GET /chunks Get raw chunk nbt data +GET /biomes Get biome of position in the world GET /buildarea Get the build area defined by the /setbuildarea chat command GET /version Get Minecraft version ``` diff --git a/src/main/java/com/gdmc/httpinterfacemod/GdmcHttpServer.java b/src/main/java/com/gdmc/httpinterfacemod/GdmcHttpServer.java index 4ab07e8..2ed8b81 100644 --- a/src/main/java/com/gdmc/httpinterfacemod/GdmcHttpServer.java +++ b/src/main/java/com/gdmc/httpinterfacemod/GdmcHttpServer.java @@ -32,5 +32,6 @@ private static void createContexts() { httpServer.createContext("/blocks", new BlocksHandler(mcServer)); httpServer.createContext("/buildarea", new BuildAreaHandler(mcServer)); httpServer.createContext("/version", new MinecraftVersionHandler(mcServer)); + httpServer.createContext("/biomes", new BiomesHandler(mcServer)); } } \ No newline at end of file diff --git a/src/main/java/com/gdmc/httpinterfacemod/handlers/BiomesHandler.java b/src/main/java/com/gdmc/httpinterfacemod/handlers/BiomesHandler.java new file mode 100644 index 0000000..45a329c --- /dev/null +++ b/src/main/java/com/gdmc/httpinterfacemod/handlers/BiomesHandler.java @@ -0,0 +1,102 @@ +package com.gdmc.httpinterfacemod.handlers; + +import com.google.gson.Gson; +import com.google.gson.JsonArray; +import com.google.gson.JsonObject; +import com.sun.net.httpserver.Headers; +import com.sun.net.httpserver.HttpExchange; +import net.minecraft.core.BlockPos; +import net.minecraft.server.MinecraftServer; +import net.minecraft.server.level.ServerLevel; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.Map; + +public class BiomesHandler extends HandlerBase { + + public BiomesHandler(MinecraftServer mcServer) { + super(mcServer); + } + + @Override + protected void internalHandle(HttpExchange httpExchange) throws IOException { + // query parameters + Map queryParams = parseQueryString(httpExchange.getRequestURI().getRawQuery()); + int x; + int y; + int z; + int dx; + int dy; + int dz; + String dimension; + + try { + x = Integer.parseInt(queryParams.getOrDefault("x", "0")); + y = Integer.parseInt(queryParams.getOrDefault("y", "0")); + z = Integer.parseInt(queryParams.getOrDefault("z", "0")); + dx = Integer.parseInt(queryParams.getOrDefault("dx", "1")); + dy = Integer.parseInt(queryParams.getOrDefault("dy", "1")); + dz = Integer.parseInt(queryParams.getOrDefault("dz", "1")); + + dimension = queryParams.getOrDefault("dimension", null); + } catch (NumberFormatException e) { + String message = "Could not parse query parameter: " + e.getMessage(); + throw new HandlerBase.HttpException(message, 400); + } + + Headers reqestHeaders = httpExchange.getRequestHeaders(); + String contentType = getHeader(reqestHeaders, "Accept", "*/*"); + boolean returnJson = contentType.equals("application/json") || contentType.equals("text/json"); + + String method = httpExchange.getRequestMethod().toLowerCase(); + String responseString; + + if (method.equals("get")) { + ServerLevel serverLevel = getServerLevel(dimension); + if (returnJson) { + JsonArray jsonArray = new JsonArray(); + for (int rangeX = x; rangeX < x + dx; rangeX++) { + for (int rangeY = y; rangeY < y + dy; rangeY++) { + for (int rangeZ = z; rangeZ < z + dz; rangeZ++) { + BlockPos blockPos = new BlockPos(rangeX, rangeY, rangeZ); + String biomeName = serverLevel.getBiome(blockPos).unwrapKey().get().location().toString(); + JsonObject json = new JsonObject(); + json.addProperty("id", biomeName); + json.addProperty("x", rangeX); + json.addProperty("y", rangeY); + json.addProperty("z", rangeZ); + jsonArray.add(json); + } + } + } + responseString = new Gson().toJson(jsonArray); + } else { + ArrayList biomesList = new ArrayList<>(); + for (int rangeX = x; rangeX < x + dx; rangeX++) { + for (int rangeY = y; rangeY < y + dy; rangeY++) { + for (int rangeZ = z; rangeZ < z + dz; rangeZ++) { + BlockPos blockPos = new BlockPos(rangeX, rangeY, rangeZ); + String biomeName = serverLevel.getBiome(blockPos).unwrapKey().get().location().toString(); + biomesList.add(rangeX + " " + rangeY + " " + rangeZ + " " + biomeName); + } + } + } + responseString = String.join("\n", biomesList); + } + } else { + throw new HandlerBase.HttpException("Method not allowed. Only GET requests are supported.", 405); + } + + Headers headers = httpExchange.getResponseHeaders(); + addDefaultHeaders(headers); + + if(returnJson) { + headers.add("Content-Type", "application/json; charset=UTF-8"); + } else { + headers.add("Content-Type", "text/plain; charset=UTF-8"); + } + + resolveRequest(httpExchange, responseString); + } +}