Revert buildin Nitro Websocket
This commit is contained in:
parent
f6d11fd5a8
commit
0acdcbb749
2
Emulator/.gitignore
vendored
2
Emulator/.gitignore
vendored
@ -5,12 +5,10 @@ compiled-builds/
|
||||
target/**
|
||||
TODO.txt
|
||||
packet.pkt
|
||||
plugins/**
|
||||
src/test/
|
||||
target/
|
||||
config.ini
|
||||
*.txt
|
||||
*.jar
|
||||
*.log
|
||||
*.zip
|
||||
.DS_Store
|
||||
|
BIN
Emulator/plugins/NitroWebsockets-3.1.jar
Normal file
BIN
Emulator/plugins/NitroWebsockets-3.1.jar
Normal file
Binary file not shown.
@ -10,16 +10,13 @@ import com.eu.habbo.habbohotel.GameEnvironment;
|
||||
import com.eu.habbo.networking.camera.CameraClient;
|
||||
import com.eu.habbo.networking.gameserver.GameServer;
|
||||
import com.eu.habbo.networking.rconserver.RCONServer;
|
||||
import com.eu.habbo.networking.websockets.NetworkChannelInitializer;
|
||||
import com.eu.habbo.plugin.PluginManager;
|
||||
import com.eu.habbo.plugin.events.emulator.EmulatorConfigUpdatedEvent;
|
||||
import com.eu.habbo.plugin.events.emulator.EmulatorLoadedEvent;
|
||||
import com.eu.habbo.plugin.events.emulator.EmulatorStartShutdownEvent;
|
||||
import com.eu.habbo.plugin.events.emulator.EmulatorStoppedEvent;
|
||||
import com.eu.habbo.plugin.events.users.UserGetIPAddressEvent;
|
||||
import com.eu.habbo.threading.ThreadPooling;
|
||||
import com.eu.habbo.util.imager.badges.BadgeImager;
|
||||
import io.netty.channel.Channel;
|
||||
import io.netty.util.AttributeKey;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.slf4j.Logger;
|
||||
@ -145,15 +142,7 @@ public final class Emulator {
|
||||
Emulator.rconServer.initializePipeline();
|
||||
Emulator.rconServer.connect();
|
||||
Emulator.badgeImager = new BadgeImager();
|
||||
Emulator.getConfig().register("websockets.whitelist", "localhost");
|
||||
Emulator.getConfig().register("ws.nitro.host", "0.0.0.0");
|
||||
Emulator.getConfig().register("ws.nitro.port", "2096");
|
||||
Emulator.getConfig().register("ws.nitro.ip.header", "");
|
||||
NetworkChannelInitializer wsChannelHandler = new NetworkChannelInitializer();
|
||||
Emulator.getGameServer().getServerBootstrap().childHandler(wsChannelHandler);
|
||||
Emulator.getGameServer().getServerBootstrap().bind(Emulator.getConfig().getValue("ws.nitro.host", "0.0.0.0"), Emulator.getConfig().getInt("ws.nitro.port", 2096)).sync();
|
||||
log.info("Websockets has started!");
|
||||
log.info("Websockets Listening on " + (wsChannelHandler.isSSL() ? "wss://" : "ws://") + Emulator.getConfig().getValue("ws.nitro.host", "0.0.0.0") + ":" + Emulator.getConfig().getInt("ws.nitro.port", 2096));
|
||||
|
||||
log.info("Arcturus Morningstar has successfully loaded.");
|
||||
log.info("System launched in: {}ms. Using {} threads!", (System.nanoTime() - startTime) / 1e6, Runtime.getRuntime().availableProcessors() * 2);
|
||||
log.info("Memory: {}/{}MB", (runtime.totalMemory() - runtime.freeMemory()) / (1024 * 1024), (runtime.freeMemory()) / (1024 * 1024));
|
||||
@ -343,19 +332,6 @@ public final class Emulator {
|
||||
return rconServer;
|
||||
}
|
||||
|
||||
public void onUserGetIPEvent(UserGetIPAddressEvent e) {
|
||||
Channel channel = e.habbo.getClient().getChannel();
|
||||
if(channel != null && channel.hasAttr(Emulator.WS_IP)) {
|
||||
String ip = channel.attr(Emulator.WS_IP).get();
|
||||
if(!ip.isEmpty()) {
|
||||
e.setUpdatedIp(ip);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated Do not use. Please use LoggerFactory.getLogger(YourClass.class) to log.
|
||||
*/
|
||||
@Deprecated
|
||||
public static Logging getLogging() {
|
||||
return logging;
|
||||
|
@ -1,74 +0,0 @@
|
||||
package com.eu.habbo.networking.websockets;
|
||||
|
||||
import com.eu.habbo.messages.PacketManager;
|
||||
import com.eu.habbo.networking.gameserver.decoders.*;
|
||||
import com.eu.habbo.networking.gameserver.encoders.GameServerMessageEncoder;
|
||||
import com.eu.habbo.networking.gameserver.encoders.GameServerMessageLogger;
|
||||
import com.eu.habbo.networking.gameserver.handlers.IdleTimeoutHandler;
|
||||
import com.eu.habbo.networking.websockets.codec.WebSocketCodec;
|
||||
import com.eu.habbo.networking.websockets.handlers.CustomHTTPHandler;
|
||||
import com.eu.habbo.networking.websockets.ssl.SSLCertificateLoader;
|
||||
import io.netty.channel.ChannelInitializer;
|
||||
import io.netty.channel.socket.SocketChannel;
|
||||
import io.netty.handler.codec.http.HttpObjectAggregator;
|
||||
import io.netty.handler.codec.http.HttpServerCodec;
|
||||
import io.netty.handler.codec.http.websocketx.WebSocketServerProtocolConfig;
|
||||
import io.netty.handler.codec.http.websocketx.WebSocketServerProtocolHandler;
|
||||
import io.netty.handler.logging.LoggingHandler;
|
||||
import io.netty.handler.ssl.SslContext;
|
||||
|
||||
public class NetworkChannelInitializer extends ChannelInitializer<SocketChannel> {
|
||||
private static final int MAX_FRAME_SIZE = 500000;
|
||||
|
||||
private final SslContext context;
|
||||
private final boolean isSSL;
|
||||
private final WebSocketServerProtocolConfig config;
|
||||
|
||||
public NetworkChannelInitializer() {
|
||||
context = SSLCertificateLoader.getContext();
|
||||
isSSL = context != null;
|
||||
config = WebSocketServerProtocolConfig.newBuilder()
|
||||
.websocketPath("/")
|
||||
.checkStartsWith(true)
|
||||
.maxFramePayloadLength(MAX_FRAME_SIZE)
|
||||
.build();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void initChannel(SocketChannel ch) {
|
||||
ch.pipeline().addLast("logger", new LoggingHandler());
|
||||
|
||||
if(isSSL) {
|
||||
ch.pipeline().addLast(context.newHandler(ch.alloc()));
|
||||
}
|
||||
ch.pipeline().addLast("httpCodec", new HttpServerCodec());
|
||||
ch.pipeline().addLast("objectAggregator", new HttpObjectAggregator(MAX_FRAME_SIZE));
|
||||
ch.pipeline().addLast("customHttpHandler", new CustomHTTPHandler());
|
||||
ch.pipeline().addLast("protocolHandler", new WebSocketServerProtocolHandler(config));
|
||||
ch.pipeline().addLast("websocketCodec", new WebSocketCodec());
|
||||
|
||||
// Decoders.
|
||||
ch.pipeline().addLast(new GamePolicyDecoder());
|
||||
ch.pipeline().addLast(new GameByteFrameDecoder());
|
||||
ch.pipeline().addLast(new GameByteDecoder());
|
||||
|
||||
if (PacketManager.DEBUG_SHOW_PACKETS) {
|
||||
ch.pipeline().addLast(new GameClientMessageLogger());
|
||||
}
|
||||
|
||||
ch.pipeline().addLast("idleEventHandler", new IdleTimeoutHandler(30, 60));
|
||||
ch.pipeline().addLast(new GameMessageRateLimit());
|
||||
ch.pipeline().addLast(new GameMessageHandler());
|
||||
|
||||
// Encoders.
|
||||
ch.pipeline().addLast("messageEncoder", new GameServerMessageEncoder());
|
||||
|
||||
if (PacketManager.DEBUG_SHOW_PACKETS) {
|
||||
ch.pipeline().addLast(new GameServerMessageLogger());
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isSSL() {
|
||||
return isSSL;
|
||||
}
|
||||
}
|
@ -1,22 +0,0 @@
|
||||
package com.eu.habbo.networking.websockets.codec;
|
||||
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.handler.codec.MessageToMessageCodec;
|
||||
import io.netty.handler.codec.http.websocketx.BinaryWebSocketFrame;
|
||||
import io.netty.handler.codec.http.websocketx.WebSocketFrame;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class WebSocketCodec extends MessageToMessageCodec<WebSocketFrame, ByteBuf> {
|
||||
@Override
|
||||
protected void encode(ChannelHandlerContext ctx, ByteBuf in, List<Object> out) throws Exception {
|
||||
out.add(new BinaryWebSocketFrame(in).retain());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void decode(ChannelHandlerContext ctx, WebSocketFrame in, List<Object> out) {
|
||||
out.add(in.content().retain());
|
||||
}
|
||||
}
|
||||
|
@ -1,64 +0,0 @@
|
||||
package com.eu.habbo.networking.websockets.handlers;
|
||||
|
||||
import com.eu.habbo.Emulator;
|
||||
import io.netty.buffer.Unpooled;
|
||||
import io.netty.channel.ChannelFutureListener;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.channel.ChannelInboundHandlerAdapter;
|
||||
import io.netty.handler.codec.http.*;
|
||||
import io.netty.util.ReferenceCountUtil;
|
||||
import com.eu.habbo.networking.websockets.utils.Utils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class CustomHTTPHandler extends ChannelInboundHandlerAdapter {
|
||||
private static final String ORIGIN_HEADER = "Origin";
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(CustomHTTPHandler.class);
|
||||
|
||||
@Override
|
||||
public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
|
||||
if(msg instanceof HttpMessage) {
|
||||
if(!handleHttpRequest(ctx, (HttpMessage) msg))
|
||||
{
|
||||
ReferenceCountUtil.release(msg);//discard message
|
||||
return;
|
||||
}
|
||||
}
|
||||
super.channelRead(ctx, msg);
|
||||
ctx.pipeline().remove(this);
|
||||
}
|
||||
|
||||
public boolean handleHttpRequest(ChannelHandlerContext ctx, HttpMessage req) {
|
||||
String origin = "error";
|
||||
String clientIP;
|
||||
String header = Emulator.getConfig().getValue("ws.nitro.ip.header", "");
|
||||
|
||||
// Check if X-Forwarded-For header is present and use the first IP as the client IP if available
|
||||
if (req.headers().contains(header)) {
|
||||
String xForwardedFor = req.headers().get(header);
|
||||
clientIP = xForwardedFor.split(",")[0].trim(); // Get the first IP in the list
|
||||
} else {
|
||||
clientIP = ctx.channel().remoteAddress().toString().substring(1).split(":")[0]; // Get the client's IP address
|
||||
}
|
||||
|
||||
try {
|
||||
if(req.headers().contains(ORIGIN_HEADER)) {
|
||||
origin = Utils.getDomainNameFromUrl(req.headers().get(ORIGIN_HEADER));
|
||||
}
|
||||
} catch (Exception ignored) { }
|
||||
|
||||
if(!Utils.isWhitelisted(origin, Emulator.getConfig().getValue("websockets.whitelist", "localhost").split(","))) {
|
||||
LOGGER.warn("Access denied for IP: {}", clientIP);
|
||||
|
||||
FullHttpResponse response = new DefaultFullHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.FORBIDDEN, Unpooled.wrappedBuffer("W.T.F are you doing?".getBytes()));
|
||||
ctx.writeAndFlush(response).addListener(ChannelFutureListener.CLOSE);
|
||||
return false;
|
||||
}
|
||||
|
||||
if(!header.isEmpty() && req.headers().contains(header)) {
|
||||
String ip = req.headers().get(header);
|
||||
ctx.channel().attr(Emulator.WS_IP).set(ip);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
@ -1,24 +0,0 @@
|
||||
package com.eu.habbo.networking.websockets.ssl;
|
||||
|
||||
import io.netty.handler.ssl.SslContext;
|
||||
import io.netty.handler.ssl.SslContextBuilder;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
public class SSLCertificateLoader {
|
||||
private static final String filePath = "ssl";
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(SSLCertificateLoader.class);
|
||||
|
||||
public static SslContext getContext() {
|
||||
SslContext context;
|
||||
try {
|
||||
context = SslContextBuilder.forServer(new File( filePath + File.separator + "cert.pem" ), new File( filePath + File.separator + "privkey.pem" )).build();
|
||||
} catch ( Exception e ) {
|
||||
LOGGER.info("Unable to load ssl: " + e.getMessage());
|
||||
context = null;
|
||||
}
|
||||
return context;
|
||||
}
|
||||
}
|
@ -1,22 +0,0 @@
|
||||
package com.eu.habbo.networking.websockets.utils;
|
||||
|
||||
import java.net.URI;
|
||||
|
||||
public class Utils {
|
||||
public static String getDomainNameFromUrl(String url) throws Exception {
|
||||
URI uri = new URI(url);
|
||||
String domain = uri.getHost();
|
||||
return domain.startsWith("www.") ? domain.substring(4) : domain;
|
||||
}
|
||||
|
||||
public static boolean isWhitelisted(String toCheck, String[] whitelist) {
|
||||
for(String whitelistEntry : whitelist) {
|
||||
if(whitelistEntry.startsWith("*")) {
|
||||
if(toCheck.endsWith(whitelistEntry.substring(1)) || ("." + toCheck).equals(whitelistEntry.substring(1))) return true;
|
||||
} else {
|
||||
if(toCheck.equals(whitelistEntry)) return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user