diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..ee44a96 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +.idea +target diff --git a/pom.xml b/pom.xml new file mode 100644 index 0000000..e7cb401 --- /dev/null +++ b/pom.xml @@ -0,0 +1,55 @@ + + + 4.0.0 + + de.steamwar + PersistentBungeeCore + 1.0 + jar + PersistentBungeeCore + + + UTF-8 + + + + + bungeecord-repo + https://oss.sonatype.org/content/repositories/snapshots + + + + + src + + + src + + **/*.java + + + + + + org.apache.maven.plugins + maven-compiler-plugin + + 8 + 8 + + + + + + + + net.md-5 + bungeecord-api + 1.12-SNAPSHOT + jar + provided + + + diff --git a/src/de/steamwar/bungeecore/Bauserver.java b/src/de/steamwar/bungeecore/Bauserver.java new file mode 100644 index 0000000..47815fd --- /dev/null +++ b/src/de/steamwar/bungeecore/Bauserver.java @@ -0,0 +1,22 @@ +package de.steamwar.bungeecore; + +import java.util.UUID; + +public class Bauserver extends Subserver { + + private final int id; + private final UUID owner; + + public Bauserver(Servertype type, String serverName, int id, UUID owner, int port, String... command) { + super(type, serverName, port, command); + this.id = id; + this.owner = owner; + } + + public int getId(){ + return id; + } + public UUID getOwner(){ + return owner; + } +} diff --git a/src/de/steamwar/bungeecore/Persistent.java b/src/de/steamwar/bungeecore/Persistent.java new file mode 100644 index 0000000..2379e4f --- /dev/null +++ b/src/de/steamwar/bungeecore/Persistent.java @@ -0,0 +1,44 @@ +package de.steamwar.bungeecore; + +import net.md_5.bungee.api.event.ProxyReloadEvent; +import net.md_5.bungee.api.plugin.Listener; +import net.md_5.bungee.api.plugin.Plugin; +import net.md_5.bungee.event.EventHandler; + +public class Persistent extends Plugin implements Listener { + + private static Persistent instance; + private static String chatPrefix = ""; + private static String lobbyServer = ""; + + @Override + public void onEnable(){ + instance = this; + } + + @Override + public void onDisable(){ + Subserver.shutdown(); + } + + @EventHandler + public void onGReload(ProxyReloadEvent e){ + + } + + public static void setLobbyServer(String lobbyServer) { + Persistent.lobbyServer = lobbyServer; + } + public static void setChatPrefix(String prefix){ + chatPrefix = prefix; + } + public static String getLobbyServer() { + return lobbyServer; + } + public static String getPrefix(){ + return chatPrefix; + } + public static Persistent getInstance() { + return instance; + } +} diff --git a/src/de/steamwar/bungeecore/Servertype.java b/src/de/steamwar/bungeecore/Servertype.java new file mode 100644 index 0000000..99a9482 --- /dev/null +++ b/src/de/steamwar/bungeecore/Servertype.java @@ -0,0 +1,6 @@ +package de.steamwar.bungeecore; + +public enum Servertype { + BAUSERVER, + ARENA +} diff --git a/src/de/steamwar/bungeecore/Subserver.java b/src/de/steamwar/bungeecore/Subserver.java new file mode 100644 index 0000000..bb184d8 --- /dev/null +++ b/src/de/steamwar/bungeecore/Subserver.java @@ -0,0 +1,171 @@ +package de.steamwar.bungeecore; + +import net.md_5.bungee.api.ProxyServer; +import net.md_5.bungee.api.config.ServerInfo; +import net.md_5.bungee.api.connection.ProxiedPlayer; +import net.md_5.bungee.api.event.ServerSwitchEvent; +import net.md_5.bungee.api.plugin.Listener; +import net.md_5.bungee.event.EventHandler; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStreamReader; +import java.io.PrintWriter; +import java.net.InetSocketAddress; +import java.util.ArrayList; +import java.util.Iterator; +import java.util.LinkedList; +import java.util.List; +import java.util.logging.Level; +import java.util.logging.Logger; + +public class Subserver implements Runnable, Listener { + + private static final List serverList = new LinkedList<>(); + private static final Logger logger = ProxyServer.getInstance().getLogger(); + + public static Subserver getSubserver(ProxiedPlayer p){ + for(Subserver s : serverList){ + if(s.onServer(p)) + return s; + } + + return null; + } + + private final String serverName; + private Process p; + private PrintWriter writer; + private ServerInfo server; + private Servertype type; + private boolean started; + + private final List cachedPlayers = new ArrayList<>(); + private final List players = new ArrayList<>(); + + public Subserver(Servertype type, String serverName, int port, String... command){ + this.started = false; + this.serverName = serverName; + this.type = type; + + ProcessBuilder pb = new ProcessBuilder(command); + InetSocketAddress address = new InetSocketAddress("127.0.0.1", port); + + try{ + this.p = pb.start(); + }catch(IOException e){ + logger.log(Level.SEVERE, "Server could not be started", e); + return; + } + + this.server = ProxyServer.getInstance().constructServerInfo( + serverName, address, "SteamWar.de - Subserver", false); + this.writer = new PrintWriter(p.getOutputStream(), true); + + ProxyServer.getInstance().getScheduler().runAsync(Persistent.getInstance(), this); + } + + public ServerInfo getServer(){ + return server; + } + + public void sendPlayer(ProxiedPlayer p){ + if(!started){ + p.sendMessage(Persistent.getPrefix() + "§7Der Server wird gestartet, einen Moment bitte..."); + cachedPlayers.add(p); + }else{ + p.connect(server); + players.add(p); + } + } + + static void shutdown(){ + try { + while (!serverList.isEmpty()) { + Subserver server = serverList.get(0); + server.writer.println("stop"); + server.p.waitFor(); + } + }catch(InterruptedException e){ + logger.log(Level.SEVERE, "Subserver shutdown interrupted!", e); + Thread.currentThread().interrupt(); + } + } + + private boolean onServer(ProxiedPlayer p){ + return cachedPlayers.contains(p) || players.contains(p); + } + + private void fatalError(){ + for(ProxiedPlayer cached : cachedPlayers){ + cached.sendMessage(Persistent.getPrefix() + "§cUnerwarteter Fehler beim Serverstart."); + } + for(ProxiedPlayer player : server.getPlayers()){ + player.connect(ProxyServer.getInstance().getServerInfo(Persistent.getLobbyServer())); + player.sendMessage(Persistent.getPrefix() + "§cUnerwarteter Fehler im Server."); + } + } + + public void run(){ + ProxyServer.getInstance().getServers().put(serverName, server); + ProxyServer.getInstance().getPluginManager().registerListener(Persistent.getInstance(), this); + serverList.add(this); + + try(BufferedReader reader = new BufferedReader(new InputStreamReader(p.getInputStream()))){ + String line = ""; + while (!started && (line = reader.readLine()) != null) { + started = line.contains(" INFO]: Done ("); //Problematisch + } + + if(line == null){ + logger.log(Level.SEVERE, "Subserver {0} stopped to early!", serverName); + fatalError(); + return; + } + + Thread.sleep(800); + + for(ProxiedPlayer cachedPlayer : cachedPlayers){ + Thread.sleep(200); + sendPlayer(cachedPlayer); + } + cachedPlayers.clear(); + + p.waitFor(); + } catch(IOException e) { + logger.log(Level.SEVERE, "Server " + serverName + " was interrupted!", e); + fatalError(); + } catch(InterruptedException e) { + logger.log(Level.SEVERE, "Server " + serverName + " was interrupted!", e); + fatalError(); + Thread.currentThread().interrupt(); + } finally { + serverList.remove(this); + ProxyServer.getInstance().getServers().remove(serverName); + ProxyServer.getInstance().getPluginManager().unregisterListener(this); + } + } + + @EventHandler + public void onServerSwitchEvent(ServerSwitchEvent e){ + ProxiedPlayer player = e.getPlayer(); + if(player.getServer().getInfo().equals(server)) + return; + + Iterator it = cachedPlayers.iterator(); + while(it.hasNext()){ + if(it.next().equals(player)){ + it.remove(); + return; + } + } + + it = players.iterator(); + while(it.hasNext()){ + if(it.next().equals(player)){ + it.remove(); + return; + } + } + } +} diff --git a/src/plugin.yml b/src/plugin.yml new file mode 100644 index 0000000..cda33ce --- /dev/null +++ b/src/plugin.yml @@ -0,0 +1,4 @@ +name: PersistentBungeeCore +main: de.steamwar.bungeecore.Persistent +version: 1.0 +author: Lixfel