Cleaned up network registry

This commit is contained in:
kuroppoi 2021-04-18 17:46:27 +02:00
parent f83cede5e1
commit 2578fddcf8
6 changed files with 112 additions and 93 deletions

View file

@ -7,6 +7,8 @@ import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import brainwine.gameserver.entity.player.PlayerManager;
import brainwine.gameserver.msgpack.MessagePackHelper;
import brainwine.gameserver.server.NetworkRegistry;
import brainwine.gameserver.server.Server;
import brainwine.gameserver.zone.ZoneManager;
@ -29,8 +31,10 @@ public class GameServer {
long startTime = System.currentTimeMillis();
logger.info("Starting GameServer ...");
GameConfiguration.init();
MessagePackHelper.init();
zoneManager = new ZoneManager();
playerManager = new PlayerManager();
NetworkRegistry.init();
server = new Server();
server.addEndpoint(5002);
ConsoleThread consoleThread = new ConsoleThread(this);

View file

@ -2,54 +2,14 @@ package brainwine.gameserver.server;
import java.io.IOException;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.msgpack.unpacker.Unpacker;
import brainwine.gameserver.reflections.ReflectionsHelper;
import brainwine.gameserver.server.commands.BlocksIgnoreCommand;
import brainwine.gameserver.server.pipeline.Connection;
@SuppressWarnings("unchecked")
public abstract class Command {
private static final Logger logger = LogManager.getLogger();
private static final Map<Integer, Class<? extends Command>> commands = new HashMap<>();
static {
Set<Class<?>> classes = ReflectionsHelper.getTypesAnnotatedWith(RegisterCommand.class);
for(Class<?> clazz : classes) {
if(!Command.class.isAssignableFrom(clazz)) {
logger.warn("Attempted to register non-command {}", clazz.getName());
continue;
}
RegisterCommand info = clazz.getAnnotation(RegisterCommand.class);
registerCommand(info.id(), (Class<? extends Command>)clazz);
}
}
public static void registerCommand(int id, Class<? extends Command> type) {
if(commands.containsKey(id)) {
logger.warn("Attempted to register duplicate command {}", type.getTypeName());
return;
}
commands.put(id, type);
}
public static Command instantiateCommand(int id) throws InstantiationException, IllegalAccessException {
if(!commands.containsKey(id)) {
return null;
}
return commands.get(id).newInstance();
}
public abstract void process(Connection connection);
/**

View file

@ -5,62 +5,14 @@ import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.msgpack.packer.Packer;
import brainwine.gameserver.reflections.ReflectionsHelper;
@SuppressWarnings("unchecked")
public abstract class Message {
private static final Logger logger = LogManager.getLogger();
private static final Map<Class<? extends Message>, Integer> messageIds = new HashMap<>();
private static final Map<Class<? extends Message>, MessageOptions> messageOptions = new HashMap<>();
static {
Set<Class<?>> classes = ReflectionsHelper.getTypesAnnotatedWith(RegisterMessage.class);
for(Class<?> clazz : classes) {
if(!Message.class.isAssignableFrom(clazz)) {
logger.warn("Attempted to register non-message {}", clazz.getName());
continue;
}
RegisterMessage info = clazz.getAnnotation(RegisterMessage.class);
registerMessage((Class<? extends Message>)clazz, info.id(), new MessageOptions(info));
}
}
public static void registerMessage(Class<? extends Message> type, int id) {
registerMessage(type, id, new MessageOptions(false, false, false, false));
}
public static void registerMessage(Class<? extends Message> type, int id, MessageOptions options) {
if(messageIds.containsKey(type)) {
logger.warn("Attempted to register duplicate message {}", type.getTypeName());
return;
}
messageIds.put(type, id);
messageOptions.put(type, options);
}
public static int getMessageId(Message message) {
return messageIds.getOrDefault(message.getClass(), 0);
}
public static MessageOptions getMessageOptions(Message message) {
return messageOptions.get(message.getClass());
}
public void pack(Packer packer) throws IOException, IllegalArgumentException, IllegalAccessException {
MessageOptions options = getMessageOptions(this);
MessageOptions options = NetworkRegistry.getMessageOptions(this);
Field[] fields = getClass().getFields();
if(options.isPrepacked()) {

View file

@ -0,0 +1,101 @@
package brainwine.gameserver.server;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import brainwine.gameserver.reflections.ReflectionsHelper;
public class NetworkRegistry {
private static final Logger logger = LogManager.getLogger();
private static final Map<Integer, Class<? extends Command>> commands = new HashMap<>();
private static final Map<Class<? extends Message>, Integer> messageIds = new HashMap<>();
private static final Map<Class<? extends Message>, MessageOptions> messageOptions = new HashMap<>();
private static boolean initialized = false;
public static void init() {
if(initialized) {
logger.warn("init() called twice");
return;
}
initialized = true;
registerCommands();
registerMessages();
}
@SuppressWarnings("unchecked")
private static void registerCommands() {
logger.info("Registering commands ...");
Set<Class<?>> classes = ReflectionsHelper.getTypesAnnotatedWith(RegisterCommand.class);
for(Class<?> clazz : classes) {
if(!Command.class.isAssignableFrom(clazz)) {
logger.warn("Attempted to register non-command {}", clazz.getName());
continue;
}
RegisterCommand info = clazz.getAnnotation(RegisterCommand.class);
registerCommand(info.id(), (Class<? extends Command>)clazz);
}
}
@SuppressWarnings("unchecked")
private static void registerMessages() {
logger.info("Registering messages ...");
Set<Class<?>> classes = ReflectionsHelper.getTypesAnnotatedWith(RegisterMessage.class);
for(Class<?> clazz : classes) {
if(!Message.class.isAssignableFrom(clazz)) {
logger.warn("Attempted to register non-message {}", clazz.getName());
continue;
}
RegisterMessage info = clazz.getAnnotation(RegisterMessage.class);
registerMessage((Class<? extends Message>)clazz, info.id(), new MessageOptions(info));
}
}
public static void registerCommand(int id, Class<? extends Command> type) {
if(commands.containsKey(id)) {
logger.warn("Attempted to register duplicate command {}", type.getTypeName());
return;
}
commands.put(id, type);
}
public static Command instantiateCommand(int id) throws InstantiationException, IllegalAccessException {
if(!commands.containsKey(id)) {
return null;
}
return commands.get(id).newInstance();
}
public static void registerMessage(Class<? extends Message> type, int id) {
registerMessage(type, id, new MessageOptions(false, false, false, false));
}
public static void registerMessage(Class<? extends Message> type, int id, MessageOptions options) {
if(messageIds.containsKey(type)) {
logger.warn("Attempted to register duplicate message {}", type.getTypeName());
return;
}
messageIds.put(type, id);
messageOptions.put(type, options);
}
public static int getMessageId(Message message) {
return messageIds.getOrDefault(message.getClass(), 0);
}
public static MessageOptions getMessageOptions(Message message) {
return messageOptions.get(message.getClass());
}
}

View file

@ -7,6 +7,7 @@ import org.msgpack.unpacker.Unpacker;
import brainwine.gameserver.msgpack.MessagePackHelper;
import brainwine.gameserver.server.Command;
import brainwine.gameserver.server.NetworkRegistry;
import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelHandlerContext;
import io.netty.handler.codec.MessageToMessageDecoder;
@ -17,7 +18,7 @@ public class CommandDecoder extends MessageToMessageDecoder<ByteBuf> {
protected void decode(ChannelHandlerContext ctx, ByteBuf buf, List<Object> out) throws Exception {
int id = buf.readByte() & 0xFF;
buf.readIntLE(); // body length
Command command = Command.instantiateCommand(id);
Command command = NetworkRegistry.instantiateCommand(id);
if(command == null) {
throw new IOException("Client sent invalid command: " + id);

View file

@ -12,6 +12,7 @@ import com.fasterxml.jackson.databind.ObjectMapper;
import brainwine.gameserver.msgpack.MessagePackHelper;
import brainwine.gameserver.server.Message;
import brainwine.gameserver.server.MessageOptions;
import brainwine.gameserver.server.NetworkRegistry;
import brainwine.gameserver.util.ZipUtils;
import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelHandlerContext;
@ -23,8 +24,8 @@ public class MessageEncoder extends MessageToByteEncoder<Message> {
@Override
protected void encode(ChannelHandlerContext ctx, Message in, ByteBuf out) throws Exception {
int id = Message.getMessageId(in);
MessageOptions options = Message.getMessageOptions(in);
int id = NetworkRegistry.getMessageId(in);
MessageOptions options = NetworkRegistry.getMessageOptions(in);
if(id == 0) {
throw new IOException("Attempted to encode unregistered message " + in.getClass());