init
commit
24828aec5b
|
@ -0,0 +1,90 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<groupId>net.krakatoa.proxy</groupId>
|
||||
<artifactId>KrakatoaProxySystem</artifactId>
|
||||
<version>1.0-SNAPSHOT</version>
|
||||
|
||||
<properties>
|
||||
<maven.compiler.source>14</maven.compiler.source>
|
||||
<maven.compiler.target>14</maven.compiler.target>
|
||||
</properties>
|
||||
|
||||
<build>
|
||||
<defaultGoal>clean install</defaultGoal>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<artifactId>maven-assembly-plugin</artifactId>
|
||||
<configuration>
|
||||
<descriptorRefs>
|
||||
<descriptorRef>jar-with-dependencies</descriptorRef>
|
||||
</descriptorRefs>
|
||||
</configuration>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>single</goal>
|
||||
</goals>
|
||||
<id>make-assembly</id>
|
||||
<phase>package</phase>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<configuration>
|
||||
<source>9</source>
|
||||
<target>9</target>
|
||||
</configuration>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>net.md-5</groupId>
|
||||
<artifactId>bungeecord-api</artifactId>
|
||||
<version>1.17-R0.1-SNAPSHOT</version>
|
||||
<type>jar</type>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<artifactId>lombok</artifactId>
|
||||
<groupId>org.projectlombok</groupId>
|
||||
<scope>provided</scope>
|
||||
<version>1.18.22</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<artifactId>Java-WebSocket</artifactId>
|
||||
<groupId>org.java-websocket</groupId>
|
||||
<version>1.5.2</version> <!-- 1.5.1 -->
|
||||
</dependency>
|
||||
<dependency>
|
||||
<artifactId>mongodb-driver-async</artifactId>
|
||||
<groupId>org.mongodb</groupId>
|
||||
<version>3.12.10</version> <!-- 3.0.4 -->
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<repositories>
|
||||
<repository>
|
||||
<id>bungeecord-repo</id>
|
||||
<url>https://oss.sonatype.org/content/repositories/snapshots</url>
|
||||
</repository>
|
||||
<!-- https://github.com/TooTallNate/Java-WebSocket -->
|
||||
<repository>
|
||||
<id>sonatype-nexus-snapshots</id>
|
||||
<releases>
|
||||
<enabled>false</enabled>
|
||||
</releases>
|
||||
<snapshots>
|
||||
<enabled>true</enabled>
|
||||
</snapshots>
|
||||
<url>https://oss.sonatype.org/content/repositories/snapshots</url>
|
||||
</repository>
|
||||
</repositories>
|
||||
</project>
|
|
@ -0,0 +1,99 @@
|
|||
package net.krakatoa.proxy;
|
||||
|
||||
import com.mongodb.async.client.MongoCollection;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.util.Arrays;
|
||||
import lombok.Getter;
|
||||
import lombok.SneakyThrows;
|
||||
import net.krakatoa.proxy.command.CodeCommand;
|
||||
import net.krakatoa.proxy.config.ConfigHandler;
|
||||
import net.krakatoa.proxy.listener.PlayerDisconnectListener;
|
||||
import net.krakatoa.proxy.listener.PostLoginListener;
|
||||
import net.krakatoa.proxy.mongo.MongoManager;
|
||||
import net.krakatoa.proxy.protocol.KraProtocol;
|
||||
import net.krakatoa.proxy.socket.SocketClient;
|
||||
import net.krakatoa.proxy.util.Formatter;
|
||||
import net.md_5.bungee.api.plugin.Plugin;
|
||||
import net.md_5.bungee.api.plugin.PluginManager;
|
||||
import org.bson.Document;
|
||||
|
||||
@Getter
|
||||
public class ProxySystem extends Plugin {
|
||||
|
||||
@Getter
|
||||
private static ProxySystem instance;
|
||||
|
||||
private ConfigHandler configHandler;
|
||||
private MongoManager mongoManager;
|
||||
private SocketClient socketClient;
|
||||
private KraProtocol kraProtocol;
|
||||
private Formatter formatter;
|
||||
|
||||
private MongoCollection<Document> players;
|
||||
|
||||
@SneakyThrows
|
||||
@Override
|
||||
public void onEnable() {
|
||||
instance = this;
|
||||
|
||||
configHandler = new ConfigHandler();
|
||||
configHandler.load();
|
||||
|
||||
kraProtocol = new KraProtocol();
|
||||
formatter = new Formatter();
|
||||
|
||||
System.out.println(
|
||||
"mongo cfg " + configHandler.getMongodbHost() + " " + configHandler.getMongodbUsername());
|
||||
|
||||
mongoManager = new MongoManager(configHandler.getMongodbHost(),
|
||||
configHandler.getMongodbPort(), configHandler.getMongodbUsername(),
|
||||
configHandler.getMongodbPassword());
|
||||
mongoManager.connect(configHandler.getMongodbDatabase());
|
||||
|
||||
try {
|
||||
socketClient = new SocketClient(
|
||||
new URI(configHandler.getWebSocketProtocol() + "://" + configHandler.getWebSocketHost()
|
||||
+ ":" + configHandler.getWebSocketPort() + "/ws?t="
|
||||
+ configHandler.getWebSocketAccessKey() + "&s=proxy-1"));
|
||||
} catch (URISyntaxException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
socketClient.connect();
|
||||
|
||||
players = mongoManager.getMongoDatabase().getCollection("players");
|
||||
|
||||
loadListeners();
|
||||
loadCommands();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDisable() {
|
||||
socketClient.getConnection().close();
|
||||
socketClient.getConnection().closeConnection(1, "");
|
||||
|
||||
instance = null;
|
||||
}
|
||||
|
||||
public void loadListeners() {
|
||||
PluginManager pluginManager = getProxy().getPluginManager();
|
||||
Arrays.asList(new PostLoginListener(), new PlayerDisconnectListener())
|
||||
.forEach(listener -> {
|
||||
pluginManager.registerListener(this, listener);
|
||||
});
|
||||
}
|
||||
|
||||
public void loadCommands() {
|
||||
PluginManager pluginManager = getProxy().getPluginManager();
|
||||
Arrays.asList(new CodeCommand("code")).forEach(listener -> {
|
||||
pluginManager.registerCommand(this, listener);
|
||||
});
|
||||
}
|
||||
|
||||
/*
|
||||
TODO: proxy ping & join only accessible for 1.17.1 clients
|
||||
|
||||
*/
|
||||
|
||||
}
|
|
@ -0,0 +1,60 @@
|
|||
package net.krakatoa.proxy.command;
|
||||
|
||||
import java.security.SecureRandom;
|
||||
import net.md_5.bungee.api.CommandSender;
|
||||
import net.md_5.bungee.api.connection.ProxiedPlayer;
|
||||
import net.md_5.bungee.api.plugin.Command;
|
||||
|
||||
public class CodeCommand extends Command {
|
||||
|
||||
public CodeCommand(String name) {
|
||||
super(name);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(CommandSender commandSender, String[] strings) {
|
||||
if (commandSender instanceof ProxiedPlayer) {
|
||||
ProxiedPlayer proxiedPlayer = (ProxiedPlayer) commandSender;
|
||||
|
||||
/*
|
||||
Document query = new Document().append("uuid", ProxySystem.getInstance().getFormatter()
|
||||
.formatUuid(proxiedPlayer.getUniqueId().toString()));
|
||||
|
||||
String voiceWebCode = generateVoiceWebCode("");
|
||||
|
||||
Bson updates = Updates.combine(Updates.set("voiceWebCode", voiceWebCode));
|
||||
|
||||
UpdateOptions options = new UpdateOptions().upsert(true);
|
||||
|
||||
try {
|
||||
ProxySystem.getInstance().getPlayerRegistrationProcess()
|
||||
.updateOne(query, updates, (updateResult, throwable) -> {
|
||||
System.out.println("Modified document count: " + updateResult.getModifiedCount());
|
||||
System.out.println("Upserted id: "
|
||||
+ updateResult.getUpsertedId()); // only contains a value when an upsert is performed
|
||||
});
|
||||
} catch (MongoException exception) {
|
||||
System.err.println("Unable to update due to an error: " + exception);
|
||||
} */
|
||||
|
||||
// TODO: add url and copy text
|
||||
//proxiedPlayer.sendMessage(new TextComponent("§eNeuer Code §c§l" + voiceWebCode));
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: use static method from other file
|
||||
public String generateVoiceWebCode(String uuid) {
|
||||
SecureRandom secureRandom = new SecureRandom();
|
||||
|
||||
String chrs = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
||||
|
||||
String customTag = secureRandom.ints(8, 0, chrs.length()).mapToObj(chrs::charAt)
|
||||
.collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString();
|
||||
|
||||
System.out.println(customTag);
|
||||
|
||||
return customTag;
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,44 @@
|
|||
package net.krakatoa.proxy.config;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import lombok.Getter;
|
||||
import net.md_5.bungee.config.Configuration;
|
||||
import net.md_5.bungee.config.ConfigurationProvider;
|
||||
import net.md_5.bungee.config.YamlConfiguration;
|
||||
|
||||
@Getter
|
||||
public class ConfigHandler {
|
||||
|
||||
private String webSocketAccessKey;
|
||||
private String webSocketProtocol;
|
||||
private String webSocketHost;
|
||||
private int webSocketPort;
|
||||
|
||||
private String webVoiceAddress;
|
||||
|
||||
private String mongodbHost;
|
||||
private int mongodbPort;
|
||||
private String mongodbDatabase;
|
||||
private String mongodbUsername;
|
||||
private String mongodbPassword;
|
||||
|
||||
public void load() throws IOException {
|
||||
// TODO change file to yaml
|
||||
Configuration configuration = ConfigurationProvider.getProvider(YamlConfiguration.class)
|
||||
.load(new File("/home/CloudNet/kraConfigs", "kraSettings.yaml"));
|
||||
|
||||
webSocketAccessKey = configuration.getString("web_socket.access_key");
|
||||
webSocketProtocol = configuration.getString("web_socket.protocol");
|
||||
webSocketHost = configuration.getString("web_socket.host");
|
||||
webSocketPort = configuration.getInt("web_socket.port");
|
||||
|
||||
webVoiceAddress = configuration.getString("web.voice_address");
|
||||
|
||||
mongodbHost = configuration.getString("mongodb.host");
|
||||
mongodbPort = configuration.getInt("mongodb.port");
|
||||
mongodbDatabase = configuration.getString("mongodb.database");
|
||||
mongodbUsername = configuration.getString("mongodb.username");
|
||||
mongodbPassword = configuration.getString("mongodb.password");
|
||||
}
|
||||
}
|
|
@ -0,0 +1,26 @@
|
|||
package net.krakatoa.proxy.listener;
|
||||
|
||||
import net.md_5.bungee.api.connection.ProxiedPlayer;
|
||||
import net.md_5.bungee.api.event.PlayerDisconnectEvent;
|
||||
import net.md_5.bungee.api.plugin.Listener;
|
||||
import net.md_5.bungee.event.EventHandler;
|
||||
|
||||
public class PlayerDisconnectListener implements Listener {
|
||||
|
||||
@EventHandler
|
||||
public void onDisconnect(PlayerDisconnectEvent event) {
|
||||
ProxiedPlayer proxiedPlayer = event.getPlayer();
|
||||
|
||||
//String uuid = ProxySystem.getInstance().getFormatter()
|
||||
// .formatUuid(proxiedPlayer.getUniqueId().toString());
|
||||
|
||||
/*
|
||||
ProxySystem.getInstance().getPlayerRegistrationProcess()
|
||||
.deleteOne(Filters.eq("uuid", uuid),
|
||||
(deleteResult, throwable) -> {
|
||||
|
||||
System.out.println("delete " + deleteResult.getDeletedCount());
|
||||
}); */
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,184 @@
|
|||
package net.krakatoa.proxy.listener;
|
||||
|
||||
import com.mongodb.client.model.Filters;
|
||||
import com.mongodb.client.model.UpdateOptions;
|
||||
import com.mongodb.client.model.Updates;
|
||||
import java.security.SecureRandom;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.function.Consumer;
|
||||
import net.krakatoa.proxy.ProxySystem;
|
||||
import net.krakatoa.proxy.protocol.KraProtocolMessage;
|
||||
import net.md_5.bungee.api.ProxyServer;
|
||||
import net.md_5.bungee.api.chat.ClickEvent;
|
||||
import net.md_5.bungee.api.chat.HoverEvent;
|
||||
import net.md_5.bungee.api.chat.HoverEvent.Action;
|
||||
import net.md_5.bungee.api.chat.TextComponent;
|
||||
import net.md_5.bungee.api.chat.hover.content.Text;
|
||||
import net.md_5.bungee.api.config.ServerInfo;
|
||||
import net.md_5.bungee.api.connection.ProxiedPlayer;
|
||||
import net.md_5.bungee.api.event.PostLoginEvent;
|
||||
import net.md_5.bungee.api.event.ServerSwitchEvent;
|
||||
import net.md_5.bungee.api.plugin.Listener;
|
||||
import net.md_5.bungee.event.EventHandler;
|
||||
import org.bson.Document;
|
||||
import org.bson.conversions.Bson;
|
||||
|
||||
public class PostLoginListener implements Listener {
|
||||
|
||||
@EventHandler
|
||||
public void onPostLogin(PostLoginEvent event) {
|
||||
ProxiedPlayer proxiedPlayer = event.getPlayer();
|
||||
|
||||
String uuid = ProxySystem.getInstance().getFormatter()
|
||||
.formatUuid(proxiedPlayer.getUniqueId().toString());
|
||||
|
||||
ProxySystem.getInstance().getPlayers()
|
||||
.find(Filters.eq("uuid", uuid))
|
||||
.first((document, throwable) -> {
|
||||
if (document == null) {
|
||||
// create player in db and send voice url
|
||||
System.out.println("create player in db");
|
||||
String voiceWebCode = generateVoiceWebCode(uuid);
|
||||
|
||||
document = new Document("uuid", uuid).append("voiceWebCode", voiceWebCode);
|
||||
|
||||
ProxySystem.getInstance().getPlayers().insertOne(document, (unused, throwable1) -> {
|
||||
System.out.println("insertOne");
|
||||
});
|
||||
|
||||
sendVoiceWebCodeUrl(proxiedPlayer, voiceWebCode);
|
||||
} else {
|
||||
// check if both sockets connected
|
||||
int cmdID = ProxySystem.getInstance().getKraProtocol().getCmdID();
|
||||
|
||||
ProxySystem.getInstance().getKraProtocol().SendMessage(11, cmdID, 1, uuid, 10, "");
|
||||
|
||||
Document finalDocument = document;
|
||||
Consumer<KraProtocolMessage> consumer = value -> {
|
||||
if (value.getArgs().equals("1")) {
|
||||
// connected! Send player to game server
|
||||
System.out.println(
|
||||
proxiedPlayer.getName() + " sockets connected! Send player to game server");
|
||||
proxiedPlayer.sendMessage(
|
||||
new TextComponent("§bWillkommen zurück §6" + proxiedPlayer.getDisplayName()));
|
||||
|
||||
ProxyServer.getInstance().getScheduler().schedule(ProxySystem.getInstance(), () -> {
|
||||
ServerInfo serverInfos = ProxyServer.getInstance().getServerInfo("NewYork-1");
|
||||
proxiedPlayer.connect(serverInfos);
|
||||
}, 2L, TimeUnit.SECONDS);
|
||||
} else {
|
||||
// not connected! Send voice url
|
||||
System.out.println(
|
||||
proxiedPlayer.getName() + " sockets not connected! Send voice url");
|
||||
|
||||
String voiceWebCode = generateVoiceWebCode(uuid);
|
||||
|
||||
Bson updates = Updates.combine(Updates.set("voiceWebCode", voiceWebCode));
|
||||
|
||||
UpdateOptions options = new UpdateOptions().upsert(true);
|
||||
|
||||
ProxySystem.getInstance().getPlayers()
|
||||
.updateOne(finalDocument, updates, options, (updateResult, throwable1) -> {
|
||||
});
|
||||
|
||||
System.out.println("voiceWebCode " + voiceWebCode);
|
||||
|
||||
sendVoiceWebCodeUrl(proxiedPlayer, voiceWebCode);
|
||||
}
|
||||
|
||||
System.out.println(
|
||||
"consumer response value " + value.getUuid() + " " + value.getCmdID());
|
||||
};
|
||||
ProxySystem.getInstance().getKraProtocol().getConsumerHashMap().put(cmdID, consumer);
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
}
|
||||
|
||||
public void sendVoiceWebCodeUrl(ProxiedPlayer proxiedPlayer, String voiceWebCode) {
|
||||
String url = ProxySystem.getInstance().getConfigHandler()
|
||||
.getWebVoiceAddress() + voiceWebCode;
|
||||
|
||||
TextComponent textComponent = new TextComponent(
|
||||
"Klicke auf den Link, um dich mit dem Voice Server zu verbinden");
|
||||
|
||||
TextComponent linkComponent = new TextComponent(url);
|
||||
linkComponent.setHoverEvent(new HoverEvent(Action.SHOW_TEXT,
|
||||
new Text(url)));
|
||||
linkComponent.setClickEvent(
|
||||
new ClickEvent(ClickEvent.Action.OPEN_URL,
|
||||
url));
|
||||
|
||||
textComponent.addExtra("\n");
|
||||
textComponent.addExtra(linkComponent);
|
||||
|
||||
proxiedPlayer.sendMessage(textComponent);
|
||||
}
|
||||
|
||||
public String generateVoiceWebCode(String uuid) {
|
||||
SecureRandom secureRandom = new SecureRandom();
|
||||
|
||||
String chrs = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
||||
|
||||
String customTag = secureRandom.ints(8, 0, chrs.length()).mapToObj(chrs::charAt)
|
||||
.collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString();
|
||||
|
||||
System.out.println(customTag);
|
||||
|
||||
|
||||
/* String chrs = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
||||
SecureRandom secureRandom = SecureRandom.getInstanceStrong();
|
||||
|
||||
String customTag = secureRandom.ints(9, 0, chrs.length()).mapToObj(chrs::charAt)
|
||||
.collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString();
|
||||
System.out.println(customTag);
|
||||
|
||||
/*AtomicBoolean avail = new AtomicBoolean(false);
|
||||
|
||||
while (!avail.get()) {
|
||||
System.out.println("while");
|
||||
secureRandom.ints(8, 0, chrs.length()).mapToObj(chrs::charAt)
|
||||
.collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString();
|
||||
System.out.println(customTag);
|
||||
|
||||
ProxySystem.getInstance().getPlayerRegistrationProcess().find(Filters.eq("webCode", chrs))
|
||||
.first((document, throwable) -> {
|
||||
if (document == null) {
|
||||
avail.set(true);
|
||||
}
|
||||
});
|
||||
}*/
|
||||
|
||||
return customTag;
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onServerSwitch(ServerSwitchEvent event) {
|
||||
ProxiedPlayer player = event.getPlayer();
|
||||
|
||||
player.sendMessage(
|
||||
new TextComponent("Switched server " + player.getServer().getInfo().getName()));
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@EventHandler
|
||||
public void onServerConnect(ServerConnectEvent event) {
|
||||
System.out.println(
|
||||
"REASON " + event.getReason() + " " + event.getPlayer().getUniqueId().toString());
|
||||
|
||||
if (!event.getReason().equals(Reason.JOIN_PROXY)) {
|
||||
System.out.println("return join proxy");
|
||||
return;
|
||||
}
|
||||
|
||||
// event.setTarget(ProxyServer.getInstance().getServerInfo("NewYork-1"));
|
||||
/*
|
||||
ProxySystem.getInstance().getKraProtocol()
|
||||
.SendMessage(11, 10, 0, event.getPlayer().getUniqueId().toString().replaceAll("-", ""), 10,
|
||||
"");
|
||||
|
||||
//event.setTarget(ProxyServer.getInstance().getServerInfo("NewYork-1"));
|
||||
} */
|
||||
}
|
|
@ -0,0 +1,39 @@
|
|||
package net.krakatoa.proxy.mongo;
|
||||
|
||||
import com.mongodb.async.client.MongoClient;
|
||||
import com.mongodb.async.client.MongoClients;
|
||||
import com.mongodb.async.client.MongoCollection;
|
||||
import com.mongodb.async.client.MongoDatabase;
|
||||
import lombok.Getter;
|
||||
import org.bson.Document;
|
||||
|
||||
public class MongoManager {
|
||||
|
||||
private final String hostname;
|
||||
private final int port;
|
||||
private final String username;
|
||||
private final String password;
|
||||
|
||||
@Getter
|
||||
private MongoDatabase mongoDatabase;
|
||||
@Getter
|
||||
private MongoClient mongoClient;
|
||||
@Getter
|
||||
private MongoCollection<Document> players;
|
||||
|
||||
public MongoManager(String hostname, int port, String username, String password) {
|
||||
this.hostname = hostname;
|
||||
this.port = port;
|
||||
this.username = username;
|
||||
this.password = password;
|
||||
}
|
||||
|
||||
public void connect(String database) {
|
||||
mongoClient = MongoClients.create(
|
||||
"mongodb://" + username + ":" + password + "@" + hostname + ":" + port + "/?authSource="
|
||||
+ database);
|
||||
|
||||
mongoDatabase = mongoClient.getDatabase(database);
|
||||
players = mongoDatabase.getCollection("players");
|
||||
}
|
||||
}
|
|
@ -0,0 +1,119 @@
|
|||
package net.krakatoa.proxy.protocol;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.function.Consumer;
|
||||
import lombok.Getter;
|
||||
import net.krakatoa.proxy.ProxySystem;
|
||||
|
||||
public class KraProtocol {
|
||||
|
||||
@Getter
|
||||
ArrayList<Integer> cmdIDs = Lists.newArrayList();
|
||||
|
||||
@Getter
|
||||
HashMap<Integer, Consumer<KraProtocolMessage>> consumerHashMap = new HashMap<>();
|
||||
|
||||
public int getCmdID() {
|
||||
if (cmdIDs.isEmpty()) {
|
||||
cmdIDs.add(10);
|
||||
return 10;
|
||||
}
|
||||
|
||||
int cmdID = cmdIDs.get(cmdIDs.size() - 1) + 1;
|
||||
|
||||
cmdIDs.add(cmdID);
|
||||
|
||||
// TODO: check max int value 2^32
|
||||
|
||||
return cmdID;
|
||||
}
|
||||
|
||||
public void SendMessage(KraProtocolMessage kraProtocolMessage) {
|
||||
SendMessage(kraProtocolMessage.getStatus(), kraProtocolMessage.getCmdID(),
|
||||
kraProtocolMessage.getDest(), kraProtocolMessage.getUuid(),
|
||||
kraProtocolMessage.getCmdNumber(), kraProtocolMessage.getArgs());
|
||||
}
|
||||
|
||||
public void SendMessage(int status, int cmdID, int dest, String uuid, int cmdNumber,
|
||||
String args) {
|
||||
System.out.println("sendMessage: " + status + " " + cmdID + " " + dest + " " + cmdNumber);
|
||||
|
||||
int argLen = args.length();
|
||||
|
||||
byte[] raw = new byte[40 + argLen];
|
||||
|
||||
raw[0] = (byte) status;
|
||||
|
||||
raw[1] = (byte) cmdID;
|
||||
raw[2] = (byte) (cmdID >> 8);
|
||||
raw[3] = (byte) (cmdID >> 16);
|
||||
raw[4] = (byte) (cmdID >> 24);
|
||||
|
||||
raw[5] = (byte) dest;
|
||||
|
||||
byte[] uuidBytes = uuid.getBytes();
|
||||
|
||||
/* for (int i = 0; i < 32; i++) {
|
||||
raw[6 + i] = uuidBytes[i];
|
||||
}*/
|
||||
|
||||
System.arraycopy(uuidBytes, 0, raw, 6, 32);
|
||||
|
||||
raw[38] = (byte) cmdNumber;
|
||||
raw[39] = (byte) (cmdNumber >> 8);
|
||||
|
||||
if (argLen > 0) {
|
||||
for (int i = 0; i < argLen; i++) {
|
||||
raw[40 + i] = (byte) args.charAt(i);
|
||||
}
|
||||
}
|
||||
|
||||
ProxySystem.getInstance().getSocketClient().SendMessage(raw);
|
||||
}
|
||||
|
||||
public KraProtocolMessage DecodeMessage(byte[] data) {
|
||||
System.out.println("start decode");
|
||||
|
||||
byte status = data[0];
|
||||
|
||||
int cmdID = Byte.toUnsignedInt(data[1]);
|
||||
|
||||
cmdID += Byte.toUnsignedInt(data[2]) * 256;
|
||||
cmdID += Byte.toUnsignedInt(data[3]) * 256 * 256;
|
||||
cmdID += Byte.toUnsignedInt(data[4]) * 256 * 256 * 256;
|
||||
|
||||
int dest = Byte.toUnsignedInt(data[5]);
|
||||
|
||||
byte[] playerUuidBytes = new byte[32];
|
||||
|
||||
System.arraycopy(data, 6, playerUuidBytes, 0, 32);
|
||||
|
||||
/* for (int i = 0; i < 32; i++) {
|
||||
playerUuidBytes[i] = data[6 + i];
|
||||
} */
|
||||
|
||||
String playerUuid = new String(playerUuidBytes, StandardCharsets.UTF_8);
|
||||
|
||||
short cmdNumber = (short) (Byte.toUnsignedInt(data[38]) + (Byte.toUnsignedInt(data[39]) * 256));
|
||||
|
||||
int argLen = data.length - 40;
|
||||
byte[] argsBytes = new byte[argLen];
|
||||
|
||||
/* for (int i = 0; i < argLen; i++) {
|
||||
argsBytes[i] = data[40 + i];
|
||||
} */
|
||||
|
||||
System.arraycopy(data, 40, argsBytes, 0, argLen);
|
||||
|
||||
String args = new String(argsBytes, StandardCharsets.UTF_8);
|
||||
|
||||
System.out.println(
|
||||
"decoded message " + status + " " + cmdID + " " + dest + " " + playerUuid + " "
|
||||
+ cmdNumber + " " + args + " ");
|
||||
|
||||
return new KraProtocolMessage(status, cmdID, dest, playerUuid, cmdNumber, args);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
package net.krakatoa.proxy.protocol;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Getter;
|
||||
|
||||
@AllArgsConstructor
|
||||
@Getter
|
||||
public class KraProtocolMessage {
|
||||
|
||||
private final byte status;
|
||||
private final int cmdID; // long
|
||||
private final int dest;
|
||||
private final String uuid;
|
||||
private final short cmdNumber;
|
||||
private final String args;
|
||||
|
||||
public int getStatus() {
|
||||
return Byte.toUnsignedInt(status);
|
||||
}
|
||||
|
||||
public int getCmdNumber() {
|
||||
return Short.toUnsignedInt(cmdNumber);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
package net.krakatoa.proxy.protocol;
|
||||
|
||||
public class KraProtocolMessageHandler {
|
||||
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
package net.krakatoa.proxy.protocol;
|
||||
|
||||
import lombok.Getter;
|
||||
|
||||
public enum KraProtocolStatus {
|
||||
|
||||
SEND(10),
|
||||
GET(11),
|
||||
MESSAGE_ALREADY_IN_QUEUE(12),
|
||||
ERROR_NO_PERMS(13),
|
||||
ERROR_TRY_AGAIN(14),
|
||||
ERROR_ARG_LEN_TOO_BIG(15),
|
||||
REPLY(16);
|
||||
|
||||
@Getter
|
||||
private final int status;
|
||||
|
||||
KraProtocolStatus(int status) {
|
||||
this.status = status;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,121 @@
|
|||
package net.krakatoa.proxy.socket;
|
||||
|
||||
import java.net.URI;
|
||||
import java.nio.ByteBuffer;
|
||||
import java.util.Arrays;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import net.krakatoa.proxy.ProxySystem;
|
||||
import net.krakatoa.proxy.protocol.KraProtocolMessage;
|
||||
import net.md_5.bungee.api.ProxyServer;
|
||||
import net.md_5.bungee.api.chat.TextComponent;
|
||||
import net.md_5.bungee.api.connection.ProxiedPlayer;
|
||||
import org.java_websocket.client.WebSocketClient;
|
||||
import org.java_websocket.handshake.ServerHandshake;
|
||||
|
||||
public class SocketClient extends WebSocketClient {
|
||||
|
||||
public SocketClient(URI uri) {
|
||||
super(uri);
|
||||
}
|
||||
|
||||
public void SendMessage(byte[] message) {
|
||||
if (isOpen()) {
|
||||
send(message);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onOpen(ServerHandshake serverHandshake) {
|
||||
System.out.println("Socket connection opened!");
|
||||
|
||||
//ProxySystem.getInstance().getKraProtocol()
|
||||
// .SendMessage(1, 126375, 248, "myuui123asdrsdasadsdasdadsadsdsa", 65017, "player joined");
|
||||
|
||||
for (ProxiedPlayer proxiedPlayer : ProxyServer.getInstance().getPlayers()) {
|
||||
proxiedPlayer.sendMessage(new TextComponent("§cSocket §8» §aConnected"));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onMessage(String s) {
|
||||
System.out.println("recv s: " + s);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onMessage(ByteBuffer byteBuffer) {
|
||||
System.out.println("recv b: " + Arrays.toString(byteBuffer.array()));
|
||||
|
||||
KraProtocolMessage kraProtocolMessage = ProxySystem.getInstance().getKraProtocol()
|
||||
.DecodeMessage(byteBuffer.array());
|
||||
|
||||
System.out.println(
|
||||
"kraProtocolMessage " + kraProtocolMessage.getCmdID() + " " + kraProtocolMessage.getArgs());
|
||||
|
||||
// remove cmdID from cmdID list
|
||||
ProxySystem.getInstance().getKraProtocol().getCmdIDs()
|
||||
.removeIf(cmdID -> cmdID == kraProtocolMessage.getCmdID());
|
||||
|
||||
System.out.println(
|
||||
"consumer ids " + ProxySystem.getInstance().getKraProtocol().getConsumerHashMap().keySet());
|
||||
|
||||
// test - mobile or voice socket connected
|
||||
if (kraProtocolMessage.getCmdNumber() == 15) {
|
||||
ProxyServer.getInstance().getScheduler().runAsync(ProxySystem.getInstance(), () -> {
|
||||
System.out.println(ProxySystem.getInstance().getFormatter()
|
||||
.stringToUuid(kraProtocolMessage.getUuid()));
|
||||
|
||||
ProxiedPlayer proxiedPlayer = ProxySystem.getInstance().getProxy()
|
||||
.getPlayer(ProxySystem.getInstance().getFormatter()
|
||||
.stringToUuid(kraProtocolMessage.getUuid()));
|
||||
|
||||
if (proxiedPlayer != null) {
|
||||
if (kraProtocolMessage.getArgs().equals("1")) {
|
||||
proxiedPlayer.sendMessage(new TextComponent("§5Mobile §8» §cConnection lost!"));
|
||||
} else {
|
||||
proxiedPlayer.sendMessage(
|
||||
new TextComponent("§bVoice §8» §cConnection lost!"));
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
ProxySystem.getInstance().getKraProtocol().getConsumerHashMap()
|
||||
.forEach((cmdID, consumer) -> {
|
||||
if (cmdID == kraProtocolMessage.getCmdID()) {
|
||||
System.out.println("accept " + cmdID + " " + kraProtocolMessage.getCmdID());
|
||||
consumer.accept(kraProtocolMessage);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onClose(int code, String reason, boolean remote) {
|
||||
System.out.println(
|
||||
"Connection! closed by " + (remote ? "remote peer" : "us") + " Code: " + code + " Reason: "
|
||||
+ reason);
|
||||
|
||||
for (ProxiedPlayer proxiedPlayer : ProxyServer.getInstance().getPlayers()) {
|
||||
proxiedPlayer.sendMessage(
|
||||
new TextComponent(
|
||||
"§cSocket §8» §c" + (remote ? "Connection! Closed by remote peer" : reason)));
|
||||
}
|
||||
|
||||
/* 1 called on plugin disable */
|
||||
if (code != 1) {
|
||||
ProxyServer.getInstance().getScheduler().schedule(ProxySystem.getInstance(), () -> {
|
||||
for (ProxiedPlayer proxiedPlayer : ProxyServer.getInstance().getPlayers()) {
|
||||
proxiedPlayer.sendMessage(new TextComponent("§cSocket §8» §7Reconnecting..."));
|
||||
}
|
||||
|
||||
System.out.println("try reconnect");
|
||||
reconnect();
|
||||
}, 3L, TimeUnit.SECONDS);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Exception e) {
|
||||
System.out.println("Error: " + e);
|
||||
//e.printStackTrace();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,18 @@
|
|||
package net.krakatoa.proxy.util;
|
||||
|
||||
import java.math.BigInteger;
|
||||
import java.util.UUID;
|
||||
|
||||
public class Formatter {
|
||||
|
||||
public String formatUuid(String uuid) {
|
||||
return uuid.replaceAll("-", "");
|
||||
}
|
||||
|
||||
public UUID stringToUuid(String s) {
|
||||
BigInteger bigInteger = new BigInteger(s.substring(0, 16), 16);
|
||||
BigInteger bigInteger1 = new BigInteger(s.substring(16, 32), 16);
|
||||
|
||||
return new UUID(bigInteger.longValue(), bigInteger1.longValue());
|
||||
}
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
name: KrakatoaProxySystem
|
||||
author: AlexanderRoese
|
||||
version: 1.0
|
||||
main: net.krakatoa.proxy.ProxySystem
|
||||
commands:
|
||||
code:
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -0,0 +1,6 @@
|
|||
name: KrakatoaProxySystem
|
||||
author: AlexanderRoese
|
||||
version: 1.0
|
||||
main: net.krakatoa.proxy.ProxySystem
|
||||
commands:
|
||||
code:
|
|
@ -0,0 +1,5 @@
|
|||
#Generated by Maven
|
||||
#Wed Oct 20 21:02:03 CEST 2021
|
||||
groupId=net.krakatoa.proxy
|
||||
artifactId=KrakatoaProxySystem
|
||||
version=1.0-SNAPSHOT
|
|
@ -0,0 +1,10 @@
|
|||
net/krakatoa/proxy/command/CodeCommand.class
|
||||
net/krakatoa/proxy/mongo/MongoManager.class
|
||||
net/krakatoa/proxy/socket/SocketClient.class
|
||||
net/krakatoa/proxy/listener/PostLoginListener.class
|
||||
net/krakatoa/proxy/ProxySystem.class
|
||||
net/krakatoa/proxy/protocol/KraProtocol.class
|
||||
net/krakatoa/proxy/util/Formatter.class
|
||||
net/krakatoa/proxy/config/ConfigHandler.class
|
||||
net/krakatoa/proxy/listener/PlayerDisconnectListener.class
|
||||
net/krakatoa/proxy/protocol/KraProtocolMessage.class
|
|
@ -0,0 +1,10 @@
|
|||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/config/ConfigHandler.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/protocol/KraProtocolMessage.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/command/CodeCommand.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/mongo/MongoManager.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/listener/PlayerDisconnectListener.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/listener/PostLoginListener.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/util/Formatter.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/ProxySystem.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/protocol/KraProtocol.java
|
||||
/home/alex/IdeaProjects/KrakatoaProxySystem/src/main/java/net/krakatoa/proxy/socket/SocketClient.java
|
Loading…
Reference in New Issue