feat: add api stuff
Some checks failed
build / build (21) (push) Failing after 4s

This commit is contained in:
TheClashFruit 2024-08-30 18:24:55 +02:00
parent 0db74b9c7b
commit f9f59d5377
Signed by: TheClashFruit
GPG key ID: 09BB24C34C2F3204
7 changed files with 210 additions and 4 deletions

View file

@ -1,6 +1,7 @@
plugins {
id 'fabric-loom' version '1.7-SNAPSHOT'
id 'maven-publish'
id 'com.github.johnrengelman.shadow' version '8.1.1'
}
version = project.mod_version
@ -26,7 +27,8 @@ dependencies {
// Fabric API. This is technically optional, but you probably want it anyway.
modImplementation "net.fabricmc.fabric-api:fabric-api:${project.fabric_version}"
implementation 'com.google.code.gson:gson:2.10.1'
}
processResources {
@ -51,6 +53,10 @@ java {
targetCompatibility = JavaVersion.VERSION_1_8
}
shadowJar {
relocate('com.google.gson', 'cc.crss.mod.deps.gson')
}
jar {
from("LICENSE") {
rename { "${it}_${project.base.archivesName.get()}"}

View file

@ -1,16 +1,26 @@
package cc.crss.mod;
import cc.crss.mod.api.ApiServer;
import net.fabricmc.api.DedicatedServerModInitializer;
import net.fabricmc.fabric.api.event.lifecycle.v1.ServerLifecycleEvents;
import net.minecraft.server.MinecraftServer;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import cc.crss.mod.util.CommandRegister;
public class CRSSMod implements DedicatedServerModInitializer {
public static final Logger LOGGER = LogManager.getLogger("crss");
@Override
public void onInitializeServer() {
LOGGER.info("CRSS initialising.");
ServerLifecycleEvents.SERVER_STARTED.register(ApiServer::createInstance);
ServerLifecycleEvents.SERVER_STOPPING.register(server -> {
ApiServer srv = ApiServer.getInstance();
srv.stop();
});
CommandRegister.registerCommands();
}
}

View file

@ -0,0 +1,127 @@
package cc.crss.mod.api;
import cc.crss.mod.api.data.ServerInfo;
import net.minecraft.MinecraftVersion;
import net.minecraft.server.MinecraftServer;
import net.minecraft.server.dedicated.DedicatedServer;
import net.minecraft.server.dedicated.MinecraftDedicatedServer;
import net.minecraft.world.dimension.DimensionType;
import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;
import static cc.crss.mod.CRSSMod.LOGGER;
public class ApiServer {
private static ApiServer instance;
public static MinecraftServer server;
private Thread thread;
public ApiServer(MinecraftServer server) {
if (instance != null)
throw new RuntimeException("API Server already started.");
ApiServer.server = server;
start();
}
public static ApiServer getInstance() {
return instance;
}
public static void createInstance(MinecraftServer server) {
instance = new ApiServer(server);
}
private void start() {
this.thread = new Thread(
new ServerRunnable(25580)
);
this.thread.start();
}
public void stop() {
this.thread.interrupt();
instance = null;
}
static class ServerRunnable implements Runnable {
private int port;
public ServerRunnable(int port) {
this.port = port;
}
@Override
public void run() {
try (ServerSocket serverSocket = new ServerSocket(port)) {
System.out.println("Server is listening on port " + port);
while (true) {
Socket clientSocket = serverSocket.accept();
clientSocket.setTcpNoDelay(true);
DataInputStream dataInputStream = new DataInputStream(
clientSocket.getInputStream()
);
DataOutputStream dataOutputStream = new DataOutputStream(
clientSocket.getOutputStream()
);
byte packetId = dataInputStream.readByte();
switch (packetId) {
case 0x00:
MinecraftServer server = ApiServer.server;
ArrayList<String> worlds = new ArrayList<>();
server.getWorlds().forEach(world -> {
worlds.add(world.getDimension().getType().toString());
});
String jsonData = new ServerInfo(
server.getVersion(),
server.getCurrentPlayerCount(),
worlds.toArray(new String[0])
).toJson();
int length = jsonData.length();
byte[] responseBytes = new byte[1 + 4 + length];
responseBytes[0] = 0x00;
responseBytes[1] = (byte) ((length >> 24) & 0xFF);
responseBytes[2] = (byte) ((length >> 16) & 0xFF);
responseBytes[3] = (byte) ((length >> 8) & 0xFF);
responseBytes[4] = (byte) (length & 0xFF);
System.arraycopy(jsonData.getBytes(), 0, responseBytes, 5, length);
dataOutputStream.write(responseBytes);
dataOutputStream.flush();
break;
default:
LOGGER.warn("Received unknown packet: {}", packetId);
break;
}
}
} catch (IOException e) {
LOGGER.error("Error starting API server", e);
}
}
}
}

View file

@ -0,0 +1,13 @@
package cc.crss.mod.api;
import cc.crss.mod.util.JsonUtil;
public class Model {
public String toJson() {
return JsonUtil.gson.toJson(this);
}
public static Object fromJson(String json, Class<? extends Model> clazz) {
return JsonUtil.gson.fromJson(json, clazz);
}
}

View file

@ -0,0 +1,39 @@
package cc.crss.mod.api.data;
import cc.crss.mod.api.Model;
public class ServerInfo extends Model {
private String version;
private Integer online;
private String[] worlds;
public ServerInfo(String version, Integer online, String[] worlds) {
this.version = version;
this.online = online;
this.worlds = worlds;
}
public String getVersion() {
return version;
}
public Integer getOnline() {
return online;
}
public String[] getWorlds() {
return worlds;
}
public void setVersion(String version) {
this.version = version;
}
public void setOnline(Integer online) {
this.online = online;
}
public void setWorlds(String[] worlds) {
this.worlds = worlds;
}
}

View file

@ -0,0 +1,11 @@
package cc.crss.mod.util;
import com.google.gson.FieldNamingPolicy;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
public class JsonUtil {
public static Gson gson = new GsonBuilder()
.setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES)
.create();
}

View file

@ -8,5 +8,5 @@
],
"injectors": {
"defaultRequire": 1
}
}
}