diff --git a/BungeeCord-Patches/0039-Improve-ServerKickEvent.patch b/BungeeCord-Patches/0039-Improve-ServerKickEvent.patch new file mode 100644 index 0000000..c47a260 --- /dev/null +++ b/BungeeCord-Patches/0039-Improve-ServerKickEvent.patch @@ -0,0 +1,139 @@ +From 26debc4163d31315a6083bb2fcc62f45333d8edc Mon Sep 17 00:00:00 2001 +From: Troy Frew +Date: Tue, 28 Jun 2016 23:00:49 -0500 +Subject: [PATCH] Improve ServerKickEvent + +ServerKickEvent traditionally will only fire if the server sends a kick packet. During a server shutdown, or server crash this event would not fire for most players. While ServerDisconnectEvent is fired it does not tell us if it was a kick/shutdown/server crash. This improvement fires the ServerKickEvent for server caused disconnections, and adds a Cause to the kick event. + +diff --git a/api/src/main/java/net/md_5/bungee/api/event/ServerKickEvent.java b/api/src/main/java/net/md_5/bungee/api/event/ServerKickEvent.java +index 0e1ef5c..ee63732 100644 +--- a/api/src/main/java/net/md_5/bungee/api/event/ServerKickEvent.java ++++ b/api/src/main/java/net/md_5/bungee/api/event/ServerKickEvent.java +@@ -44,6 +44,12 @@ public class ServerKickEvent extends Event implements Cancellable + * State in which the kick occured. + */ + private State state; ++ // Waterfall start ++ /** ++ * Circumstances which led to the kick. ++ */ ++ private Cause cause; ++ // Waterfall end + + public enum State + { +@@ -51,6 +57,14 @@ public class ServerKickEvent extends Event implements Cancellable + CONNECTING, CONNECTED, UNKNOWN; + } + ++ // Waterfall start ++ public enum Cause ++ { ++ ++ SERVER, LOST_CONNECTION, EXCEPTION, UNKNOWN; ++ } ++ // Waterfall end ++ + @Deprecated + public ServerKickEvent(ProxiedPlayer player, BaseComponent[] kickReasonComponent, ServerInfo cancelServer) + { +@@ -63,14 +77,23 @@ public class ServerKickEvent extends Event implements Cancellable + this( player, player.getServer().getInfo(), kickReasonComponent, cancelServer, state ); + } + ++ // Waterfall start ++ @Deprecated + public ServerKickEvent(ProxiedPlayer player, ServerInfo kickedFrom, BaseComponent[] kickReasonComponent, ServerInfo cancelServer, State state) + { ++ this( player, kickedFrom, kickReasonComponent, cancelServer, state, Cause.UNKNOWN ); ++ } ++ ++ public ServerKickEvent(ProxiedPlayer player, ServerInfo kickedFrom, BaseComponent[] kickReasonComponent, ServerInfo cancelServer, State state, Cause cause) ++ { + this.player = player; + this.kickedFrom = kickedFrom; + this.kickReasonComponent = kickReasonComponent; + this.cancelServer = cancelServer; + this.state = state; ++ this.cause = cause; + } ++ // Waterfall end + + @Deprecated + public String getKickReason() +diff --git a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java +index f1ccd72..beb8fa6 100644 +--- a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java ++++ b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java +@@ -305,7 +305,7 @@ public class ServerConnector extends PacketHandler + public void handle(Kick kick) throws Exception + { + ServerInfo def = user.updateAndGetNextServer( target ); +- ServerKickEvent event = new ServerKickEvent( user, target, ComponentSerializer.parse( kick.getMessage() ), def, ServerKickEvent.State.CONNECTING ); ++ ServerKickEvent event = new ServerKickEvent( user, target, ComponentSerializer.parse( kick.getMessage() ), def, ServerKickEvent.State.CONNECTING, ServerKickEvent.Cause.SERVER ); // Waterfall + if ( event.getKickReason().toLowerCase().contains( "outdated" ) && def != null ) + { + // Pre cancel the event if we are going to try another server +diff --git a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java +index 017c2b2..8ce578e 100644 +--- a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java ++++ b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java +@@ -59,16 +59,19 @@ public class DownstreamBridge extends PacketHandler + return; + } + +- ServerInfo def = bungee.getServerInfo( con.getPendingConnection().getListener().getFallbackServer() ); +- if ( server.getInfo() != def ) ++ // Waterfall start ++ ServerInfo def = con.updateAndGetNextServer( server.getInfo() ); ++ ServerKickEvent event = bungee.getPluginManager().callEvent( new ServerKickEvent( con, server.getInfo(), TextComponent.fromLegacyText( bungee.getTranslation( "server_went_down" ) ), def, ServerKickEvent.State.CONNECTED, ServerKickEvent.Cause.EXCEPTION ) ); ++ if ( event.isCancelled() && event.getCancelServer() != null ) + { + server.setObsolete( true ); +- con.connectNow( def ); +- con.sendMessage( bungee.getTranslation( "server_went_down" ) ); +- } else ++ con.connectNow( event.getCancelServer() ); ++ } ++ else + { +- con.disconnect( Util.exception( t ) ); ++ con.disconnect0( event.getKickReasonComponent() ); + } ++ // Waterfall end + } + + @Override +@@ -83,7 +86,19 @@ public class DownstreamBridge extends PacketHandler + + if ( !server.isObsolete() ) + { +- con.disconnect( bungee.getTranslation( "lost_connection" ) ); ++ // Waterfall start ++ ServerInfo def = con.updateAndGetNextServer( server.getInfo() ); ++ ServerKickEvent event = bungee.getPluginManager().callEvent( new ServerKickEvent( con, server.getInfo(), TextComponent.fromLegacyText( bungee.getTranslation( "lost_connection" ) ), def, ServerKickEvent.State.CONNECTED, ServerKickEvent.Cause.LOST_CONNECTION ) ); ++ if ( event.isCancelled() && event.getCancelServer() != null ) ++ { ++ server.setObsolete( true ); ++ con.connectNow( event.getCancelServer() ); ++ } ++ else ++ { ++ con.disconnect0( event.getKickReasonComponent() ); ++ } ++ // Waterfall end + } + + ServerDisconnectEvent serverDisconnectEvent = new ServerDisconnectEvent( con, server.getInfo() ); +@@ -454,7 +469,7 @@ public class DownstreamBridge extends PacketHandler + { + def = null; + } +- ServerKickEvent event = bungee.getPluginManager().callEvent( new ServerKickEvent( con, server.getInfo(), ComponentSerializer.parse( kick.getMessage() ), def, ServerKickEvent.State.CONNECTED ) ); ++ ServerKickEvent event = bungee.getPluginManager().callEvent( new ServerKickEvent( con, server.getInfo(), ComponentSerializer.parse( kick.getMessage() ), def, ServerKickEvent.State.CONNECTED, ServerKickEvent.Cause.SERVER ) ); // Waterfall + if ( event.isCancelled() && event.getCancelServer() != null ) + { + con.connectNow( event.getCancelServer() ); +-- +2.9.0 +