mirror of
https://github.com/TuxCoding/FastLogin.git
synced 2025-07-30 18:57:31 +02:00
Send the correct kick packet to the client in order to show the reason
This commit is contained in:
16
README.md
16
README.md
@ -1,11 +1,19 @@
|
|||||||
# FastLogin
|
# FastLogin
|
||||||
|
|
||||||
Checks if a minecraft player has a valid premium (paid account). If so, they can skip offline authentification.
|
Checks if a minecraft player has a valid premium (paid account). If so, they can skip offline authentication.
|
||||||
|
|
||||||
Requirements:
|
###Commands:
|
||||||
|
* /premium Marks the invoker as paid account
|
||||||
|
* /premium [playername] Mark player specified as a paid account
|
||||||
|
|
||||||
|
###Premissions:
|
||||||
|
* fastlogin.command.premium
|
||||||
|
* fastlogin.command.premium.others
|
||||||
|
|
||||||
|
###Requirements:
|
||||||
* [ProtocolLib](http://www.spigotmc.org/resources/protocollib.1997/)
|
* [ProtocolLib](http://www.spigotmc.org/resources/protocollib.1997/)
|
||||||
* Bukkit 1.8.8
|
* Tested Bukkit 1.8.8 (could also work with other versions)
|
||||||
* Java 8 or above
|
* Java 7 or above
|
||||||
* An auth plugin. Supported Plugins:
|
* An auth plugin. Supported Plugins:
|
||||||
* [AuthMe](http://dev.bukkit.org/bukkit-plugins/authme-reloaded/)
|
* [AuthMe](http://dev.bukkit.org/bukkit-plugins/authme-reloaded/)
|
||||||
* [xAuth](http://dev.bukkit.org/bukkit-plugins/xauth/)
|
* [xAuth](http://dev.bukkit.org/bukkit-plugins/xauth/)
|
||||||
|
9
pom.xml
9
pom.xml
@ -8,7 +8,7 @@
|
|||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
|
|
||||||
<name>FastLogin</name>
|
<name>FastLogin</name>
|
||||||
<version>0.2.2</version>
|
<version>0.2.3</version>
|
||||||
<inceptionYear>2015</inceptionYear>
|
<inceptionYear>2015</inceptionYear>
|
||||||
<url>https://github.com/games647/FastLogin</url>
|
<url>https://github.com/games647/FastLogin</url>
|
||||||
<description>
|
<description>
|
||||||
@ -127,12 +127,14 @@
|
|||||||
<groupId>fr.xephi</groupId>
|
<groupId>fr.xephi</groupId>
|
||||||
<artifactId>authme</artifactId>
|
<artifactId>authme</artifactId>
|
||||||
<version>5.0-SNAPSHOT</version>
|
<version>5.0-SNAPSHOT</version>
|
||||||
|
<optional>true</optional>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>de.luricos.bukkit</groupId>
|
<groupId>de.luricos.bukkit</groupId>
|
||||||
<artifactId>xAuth</artifactId>
|
<artifactId>xAuth</artifactId>
|
||||||
<version>2.6</version>
|
<version>2.6</version>
|
||||||
|
<optional>true</optional>
|
||||||
<!--These artifacts produce conflicts on downloading-->
|
<!--These artifacts produce conflicts on downloading-->
|
||||||
<exclusions>
|
<exclusions>
|
||||||
<exclusion>
|
<exclusion>
|
||||||
@ -146,10 +148,12 @@
|
|||||||
</exclusions>
|
</exclusions>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<!--No maven repository :(-->
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>de.st_ddt.crazy</groupId>
|
<groupId>de.st_ddt.crazy</groupId>
|
||||||
<artifactId>CrazyCore</artifactId>
|
<artifactId>CrazyCore</artifactId>
|
||||||
<version>10.7.7</version>
|
<version>10.7.7</version>
|
||||||
|
<optional>true</optional>
|
||||||
<scope>system</scope>
|
<scope>system</scope>
|
||||||
<systemPath>${project.basedir}/lib/CrazyCore v10.7.7.jar</systemPath>
|
<systemPath>${project.basedir}/lib/CrazyCore v10.7.7.jar</systemPath>
|
||||||
</dependency>
|
</dependency>
|
||||||
@ -158,14 +162,17 @@
|
|||||||
<groupId>de.st_ddt.crazy</groupId>
|
<groupId>de.st_ddt.crazy</groupId>
|
||||||
<artifactId>CrazyLogin</artifactId>
|
<artifactId>CrazyLogin</artifactId>
|
||||||
<version>7.23</version>
|
<version>7.23</version>
|
||||||
|
<optional>true</optional>
|
||||||
<scope>system</scope>
|
<scope>system</scope>
|
||||||
<systemPath>${project.basedir}/lib/CrazyLogin v7.23.2.jar</systemPath>
|
<systemPath>${project.basedir}/lib/CrazyLogin v7.23.2.jar</systemPath>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<!--Maven repo down :(-->
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>me.lenis0012.ls</groupId>
|
<groupId>me.lenis0012.ls</groupId>
|
||||||
<artifactId>LoginSecurity</artifactId>
|
<artifactId>LoginSecurity</artifactId>
|
||||||
<version>2.0.10</version>
|
<version>2.0.10</version>
|
||||||
|
<optional>true</optional>
|
||||||
<scope>system</scope>
|
<scope>system</scope>
|
||||||
<systemPath>${project.basedir}/lib/LoginSecurity v2.0.10.jar</systemPath>
|
<systemPath>${project.basedir}/lib/LoginSecurity v2.0.10.jar</systemPath>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
@ -149,7 +149,7 @@ public class FastLogin extends JavaPlugin {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (authPluginHook == null) {
|
if (authPluginHook == null) {
|
||||||
//run this check for exceptions and not found plugins
|
//run this check for exceptions (errors) and not found plugins
|
||||||
getLogger().warning("No support offline Auth plugin found. ");
|
getLogger().warning("No support offline Auth plugin found. ");
|
||||||
getLogger().warning("Disabling this plugin...");
|
getLogger().warning("Disabling this plugin...");
|
||||||
|
|
||||||
|
@ -7,6 +7,7 @@ import com.comphenix.protocol.events.PacketContainer;
|
|||||||
import com.comphenix.protocol.events.PacketEvent;
|
import com.comphenix.protocol.events.PacketEvent;
|
||||||
import com.comphenix.protocol.injector.server.TemporaryPlayerFactory;
|
import com.comphenix.protocol.injector.server.TemporaryPlayerFactory;
|
||||||
import com.comphenix.protocol.reflect.FuzzyReflection;
|
import com.comphenix.protocol.reflect.FuzzyReflection;
|
||||||
|
import com.comphenix.protocol.wrappers.WrappedChatComponent;
|
||||||
import com.comphenix.protocol.wrappers.WrappedGameProfile;
|
import com.comphenix.protocol.wrappers.WrappedGameProfile;
|
||||||
import com.github.games647.fastlogin.Encryption;
|
import com.github.games647.fastlogin.Encryption;
|
||||||
import com.github.games647.fastlogin.FastLogin;
|
import com.github.games647.fastlogin.FastLogin;
|
||||||
@ -137,14 +138,29 @@ public class EncryptionPacketListener extends PacketAdapter {
|
|||||||
packetEvent.setCancelled(true);
|
packetEvent.setCancelled(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void disconnect(PacketEvent packetEvent, String kickMessage, Level logLevel, String logMessage
|
private void disconnect(PacketEvent packetEvent, String kickReason, Level logLevel, String logMessage
|
||||||
, Object... arguments) {
|
, Object... arguments) {
|
||||||
plugin.getLogger().log(logLevel, logMessage, arguments);
|
plugin.getLogger().log(logLevel, logMessage, arguments);
|
||||||
packetEvent.getPlayer().kickPlayer(kickMessage);
|
kickPlayer(packetEvent.getPlayer(), kickReason);
|
||||||
//cancel the event in order to prevent the server receiving an invalid packet
|
//cancel the event in order to prevent the server receiving an invalid packet
|
||||||
packetEvent.setCancelled(true);
|
packetEvent.setCancelled(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void kickPlayer(Player player, String reason) {
|
||||||
|
PacketContainer kickPacket = protocolManager.createPacket(PacketType.Login.Server.DISCONNECT);
|
||||||
|
kickPacket.getChatComponents().write(0, WrappedChatComponent.fromText(reason));
|
||||||
|
|
||||||
|
try {
|
||||||
|
//send kick packet at login state
|
||||||
|
//the normal event.getPlayer.kickPlayer(String) method does only work at play state
|
||||||
|
protocolManager.sendServerPacket(player, kickPacket);
|
||||||
|
//tell the server that we want to close the connection
|
||||||
|
player.kickPlayer("Disconnect");
|
||||||
|
} catch (InvocationTargetException ex) {
|
||||||
|
plugin.getLogger().log(Level.SEVERE, "Error sending kickpacket", ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private Object getNetworkManager(Player player)
|
private Object getNetworkManager(Player player)
|
||||||
throws SecurityException, IllegalAccessException, NoSuchFieldException {
|
throws SecurityException, IllegalAccessException, NoSuchFieldException {
|
||||||
Object injector = TemporaryPlayerFactory.getInjectorFromPlayer(player);
|
Object injector = TemporaryPlayerFactory.getInjectorFromPlayer(player);
|
||||||
@ -178,8 +194,8 @@ public class EncryptionPacketListener extends PacketAdapter {
|
|||||||
//catch not only ioexceptions also parse and NPE on unexpected json format
|
//catch not only ioexceptions also parse and NPE on unexpected json format
|
||||||
plugin.getLogger().log(Level.WARNING, "Failed to verify if session is valid", ex);
|
plugin.getLogger().log(Level.WARNING, "Failed to verify if session is valid", ex);
|
||||||
}
|
}
|
||||||
//this connection doesn't need to be closed. So can make use of keep alive in java
|
|
||||||
|
|
||||||
|
//this connection doesn't need to be closed. So can make use of keep alive in java
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -191,11 +207,12 @@ public class EncryptionPacketListener extends PacketAdapter {
|
|||||||
WrappedGameProfile fakeProfile = WrappedGameProfile.fromOfflinePlayer(Bukkit.getOfflinePlayer(username));
|
WrappedGameProfile fakeProfile = WrappedGameProfile.fromOfflinePlayer(Bukkit.getOfflinePlayer(username));
|
||||||
startPacket.getGameProfiles().write(0, fakeProfile);
|
startPacket.getGameProfiles().write(0, fakeProfile);
|
||||||
try {
|
try {
|
||||||
|
//we don't want to handle our own packets so ignore filters
|
||||||
protocolManager.recieveClientPacket(from, startPacket, false);
|
protocolManager.recieveClientPacket(from, startPacket, false);
|
||||||
} catch (InvocationTargetException | IllegalAccessException ex) {
|
} catch (InvocationTargetException | IllegalAccessException ex) {
|
||||||
plugin.getLogger().log(Level.WARNING, "Failed to fake a new start packet", ex);
|
plugin.getLogger().log(Level.WARNING, "Failed to fake a new start packet", ex);
|
||||||
//cancel the event in order to prevent the server receiving an invalid packet
|
//cancel the event in order to prevent the server receiving an invalid packet
|
||||||
from.kickPlayer("Error occurred");
|
kickPlayer(from, "Error occured");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -32,11 +32,13 @@ public class PlayerListener implements Listener {
|
|||||||
//check if it's the same player as we checked before
|
//check if it's the same player as we checked before
|
||||||
if (session != null && session.getUsername().equals(player.getName())
|
if (session != null && session.getUsername().equals(player.getName())
|
||||||
&& session.isVerified()) {
|
&& session.isVerified()) {
|
||||||
|
//java 8
|
||||||
// Bukkit.getScheduler().runTaskLater(plugin, () -> {
|
// Bukkit.getScheduler().runTaskLater(plugin, () -> {
|
||||||
// if (player.isOnline()) {
|
// if (player.isOnline()) {
|
||||||
// plugin.getLogger().log(Level.FINER, "Logging player {0} in", player.getName());
|
// plugin.getLogger().log(Level.FINER, "Logging player {0} in", player.getName());
|
||||||
// authPlugin.forceLogin(player);
|
// authPlugin.forceLogin(player);
|
||||||
// }
|
// }
|
||||||
|
//java 7+
|
||||||
Bukkit.getScheduler().runTaskLater(plugin, new Runnable() {
|
Bukkit.getScheduler().runTaskLater(plugin, new Runnable() {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -47,7 +49,7 @@ public class PlayerListener implements Listener {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
//Wait before auth plugin initializes the player
|
//Wait before auth plugin initializes the player
|
||||||
}, 1 * 20L);
|
}, 2 * 20L);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -75,7 +75,7 @@ public class StartPacketListener extends PacketAdapter {
|
|||||||
plugin.getLogger().log(Level.FINER, "Player {0} with {1} connecting to the server"
|
plugin.getLogger().log(Level.FINER, "Player {0} with {1} connecting to the server"
|
||||||
, new Object[]{sessionKey, username});
|
, new Object[]{sessionKey, username});
|
||||||
//do premium login process
|
//do premium login process
|
||||||
if (isPremium(username)) {
|
if (plugin.getEnabledPremium().contains(username) && isPremium(username)) {
|
||||||
//minecraft server implementation
|
//minecraft server implementation
|
||||||
//https://github.com/bergerkiller/CraftSource/blob/master/net.minecraft.server/LoginListener.java#L161
|
//https://github.com/bergerkiller/CraftSource/blob/master/net.minecraft.server/LoginListener.java#L161
|
||||||
sentEncryptionRequest(sessionKey, username, player, packetEvent);
|
sentEncryptionRequest(sessionKey, username, player, packetEvent);
|
||||||
@ -84,7 +84,7 @@ public class StartPacketListener extends PacketAdapter {
|
|||||||
|
|
||||||
private boolean isPremium(String playerName) {
|
private boolean isPremium(String playerName) {
|
||||||
//check if it's a valid playername and the user activated fast logins
|
//check if it's a valid playername and the user activated fast logins
|
||||||
if (playernameMatcher.matcher(playerName).matches() && plugin.getEnabledPremium().contains(playerName)) {
|
if (playernameMatcher.matcher(playerName).matches()) {
|
||||||
//only make a API call if the name is valid existing mojang account
|
//only make a API call if the name is valid existing mojang account
|
||||||
try {
|
try {
|
||||||
HttpURLConnection connection = plugin.getConnection(UUID_LINK + playerName);
|
HttpURLConnection connection = plugin.getConnection(UUID_LINK + playerName);
|
||||||
@ -119,7 +119,7 @@ public class StartPacketListener extends PacketAdapter {
|
|||||||
random.nextBytes(verifyToken);
|
random.nextBytes(verifyToken);
|
||||||
newPacket.getByteArrays().write(0, verifyToken);
|
newPacket.getByteArrays().write(0, verifyToken);
|
||||||
|
|
||||||
protocolManager.sendServerPacket(player, newPacket, false);
|
protocolManager.sendServerPacket(player, newPacket);
|
||||||
|
|
||||||
//cancel only if the player has a paid account otherwise login as normal offline player
|
//cancel only if the player has a paid account otherwise login as normal offline player
|
||||||
packetEvent.setCancelled(true);
|
packetEvent.setCancelled(true);
|
||||||
|
@ -19,9 +19,9 @@ softdepend:
|
|||||||
- LoginSecurity
|
- LoginSecurity
|
||||||
|
|
||||||
commands:
|
commands:
|
||||||
premium:
|
${project.artifactId}.:
|
||||||
description: 'Marks the invoker or the player specified as premium'
|
description: 'Marks the invoker or the player specified as premium'
|
||||||
aliases: [prem, fastlogin, loginfast]
|
aliases: [prem, premium, loginfast]
|
||||||
usage: /<command> [player]
|
usage: /<command> [player]
|
||||||
permission: ${project.artifactId}.command.premium
|
permission: ${project.artifactId}.command.premium
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user