feat: improved UserManager
This commit is contained in:
parent
0f559d09a5
commit
9e894a370e
@ -1,5 +1,6 @@
|
|||||||
package uulm.teamname.marvelous.server.netconnector;
|
package uulm.teamname.marvelous.server.netconnector;
|
||||||
|
|
||||||
|
import org.java_websocket.framing.CloseFrame;
|
||||||
import org.tinylog.Logger;
|
import org.tinylog.Logger;
|
||||||
import uulm.teamname.marvelous.gamelibrary.json.JSON;
|
import uulm.teamname.marvelous.gamelibrary.json.JSON;
|
||||||
import uulm.teamname.marvelous.gamelibrary.json.ValidationUtility;
|
import uulm.teamname.marvelous.gamelibrary.json.ValidationUtility;
|
||||||
@ -114,21 +115,23 @@ public class UserManager {
|
|||||||
if (parsedMessage instanceof HelloServerMessage) {
|
if (parsedMessage instanceof HelloServerMessage) {
|
||||||
Logger.trace("Message is instanceof HelloServerMessage, initiating handshake");
|
Logger.trace("Message is instanceof HelloServerMessage, initiating handshake");
|
||||||
handshake(conn, (HelloServerMessage) parsedMessage);
|
handshake(conn, (HelloServerMessage) parsedMessage);
|
||||||
|
|
||||||
} else if (parsedMessage instanceof ReconnectMessage) {
|
} else if (parsedMessage instanceof ReconnectMessage) {
|
||||||
Logger.trace("Message is instanceof ReconnectMessage, initiating reconnect");
|
Logger.trace("Message is instanceof ReconnectMessage, initiating reconnect");
|
||||||
reconnectClient(conn, (ReconnectMessage) parsedMessage);
|
reconnectClient(conn, (ReconnectMessage) parsedMessage);
|
||||||
|
|
||||||
} else if (parsedMessage instanceof PlayerReadyMessage) {
|
} else if (parsedMessage instanceof PlayerReadyMessage) {
|
||||||
Logger.trace("Message is instanceof PlayerReadyMessage, assigning lobby");
|
Logger.trace("Message is instanceof PlayerReadyMessage, assigning lobby");
|
||||||
assignLobby(conn, (PlayerReadyMessage) parsedMessage);
|
playerReady(conn, (PlayerReadyMessage) parsedMessage);
|
||||||
|
|
||||||
} else if (parsedMessage instanceof CharacterSelectionMessage) {
|
} else if (parsedMessage instanceof CharacterSelectionMessage) {
|
||||||
Logger.trace("Message is instanceof CharacterSelectionMessage, passing to LobbyConnection");
|
Logger.trace("Message is instanceof CharacterSelectionMessage, passing to LobbyConnection");
|
||||||
charactersSelected(conn, (CharacterSelectionMessage) parsedMessage);
|
charactersSelected(conn, (CharacterSelectionMessage) parsedMessage);
|
||||||
|
|
||||||
} else if (parsedMessage instanceof RequestMessage) {
|
} else if (parsedMessage instanceof RequestMessage) {
|
||||||
Logger.trace("Message is instanceof RequestMessage, passing to LobbyConnection");
|
Logger.trace("Message is instanceof RequestMessage, passing to LobbyConnection");
|
||||||
relayRequestMessage(conn, (RequestMessage) parsedMessage);
|
relayRequestMessage(conn, (RequestMessage) parsedMessage);
|
||||||
}
|
} else {
|
||||||
|
|
||||||
else {
|
|
||||||
Logger.debug("Message '{}' has invalid type, Error will be sent");
|
Logger.debug("Message '{}' has invalid type, Error will be sent");
|
||||||
sendError(conn, String.format(
|
sendError(conn, String.format(
|
||||||
"Message '%s' has invalid type, and cannot be processed on the server",
|
"Message '%s' has invalid type, and cannot be processed on the server",
|
||||||
@ -182,7 +185,7 @@ public class UserManager {
|
|||||||
var clientID = readyToReconnect.get(conn);
|
var clientID = readyToReconnect.get(conn);
|
||||||
var participantToRestore = activeParticipants.get(clientID);
|
var participantToRestore = activeParticipants.get(clientID);
|
||||||
|
|
||||||
participantToRestore.setConnection(conn);
|
lobbyManager.restoreConnection(conn, participantToRestore);
|
||||||
|
|
||||||
synchronized (readyToReconnect) {
|
synchronized (readyToReconnect) {
|
||||||
readyToReconnect.remove(conn);
|
readyToReconnect.remove(conn);
|
||||||
@ -190,10 +193,10 @@ public class UserManager {
|
|||||||
synchronized (inGame) {
|
synchronized (inGame) {
|
||||||
inGame.put(conn, participantToRestore);
|
inGame.put(conn, participantToRestore);
|
||||||
}
|
}
|
||||||
|
lobbyManager.restoreConnection(conn, participantToRestore);
|
||||||
// activeParticipants remains the same, as no players have been removed from the game
|
// activeParticipants remains the same, as no players have been removed from the game
|
||||||
} else {
|
} else {
|
||||||
Logger.debug(
|
Logger.debug("Client {} refused reconnection, will therefore be put into readyToConnect clients",
|
||||||
"Client {} refused reconnection, will therefore be put into readyToConnect clients",
|
|
||||||
conn);
|
conn);
|
||||||
|
|
||||||
var clientID = readyToReconnect.get(conn);
|
var clientID = readyToReconnect.get(conn);
|
||||||
@ -207,26 +210,40 @@ public class UserManager {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void assignLobby(WebSocket conn, PlayerReadyMessage message) {
|
void playerReady(WebSocket conn, PlayerReadyMessage message) {
|
||||||
if (readyToReconnect.containsKey(conn) || readyToConnect.containsKey(conn)) {
|
if (!message.startGame) {
|
||||||
|
removeUser(conn);
|
||||||
|
} else if (readyToReconnect.containsKey(conn) || readyToConnect.containsKey(conn)) {
|
||||||
|
Logger.trace("Connecting client to server");
|
||||||
|
SUID suid;
|
||||||
if (readyToConnect.containsKey(conn)) {
|
if (readyToConnect.containsKey(conn)) {
|
||||||
|
Logger.trace("Client in readyToConnect state, removing from list");
|
||||||
synchronized (readyToConnect) {
|
synchronized (readyToConnect) {
|
||||||
|
suid = readyToConnect.get(conn);
|
||||||
readyToConnect.remove(conn);
|
readyToConnect.remove(conn);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
Logger.trace("Client in readyToReconnect state, removing from list");
|
||||||
synchronized (readyToReconnect) {
|
synchronized (readyToReconnect) {
|
||||||
|
suid = readyToReconnect.get(conn);
|
||||||
readyToReconnect.remove(conn);
|
readyToReconnect.remove(conn);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Participant participant;
|
||||||
|
Logger.trace("Letting LobbyManager assign lobby to client");
|
||||||
synchronized (inGame) {
|
synchronized (inGame) {
|
||||||
var participant = lobbyManager.assignLobbyToConnection(conn, "SomeName", message);
|
participant = lobbyManager.assignLobbyToConnection(conn, suid.getName(), message);
|
||||||
inGame.put(conn, participant);
|
inGame.put(conn, participant);
|
||||||
}
|
}
|
||||||
|
Logger.trace("Adding participants to activeParticipants for reconnection possibilities");
|
||||||
|
synchronized (activeParticipants) {
|
||||||
|
activeParticipants.put(suid, participant);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
Logger.debug(
|
Logger.debug(
|
||||||
"WebSocket {} sent PlayerReadyMessage to server while not ready to connect, sending error",
|
"WebSocket {} sent PlayerReadyMessage to server while not in connection ready state, " +
|
||||||
conn);
|
"sending error", conn);
|
||||||
sendError(conn, "Invalid message, as client is not ready to connect");
|
sendError(conn, "Invalid message, as client is not in a connection-ready state");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -252,6 +269,33 @@ public class UserManager {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Method to call when removing a user from the game, e.g. on player timeout, or end of match
|
||||||
|
* @param conn is the connection to close
|
||||||
|
*/
|
||||||
|
public void removeUser(WebSocket conn) {
|
||||||
|
Logger.debug("Removing user from game");
|
||||||
|
if (conn == null) {
|
||||||
|
Logger.trace("Tried to remove user but connection was null, ignoring");
|
||||||
|
} else if (!isUserConnected(conn)) {
|
||||||
|
Logger.warn("Tried to remove non-connected user. This is probably a bug.");
|
||||||
|
} else {
|
||||||
|
if (inGame.containsKey(conn)) {
|
||||||
|
var participant = inGame.get(conn);
|
||||||
|
Logger.debug("Removing reconnect possibility for participant '{}'", participant.name);
|
||||||
|
var suid = new SUID(participant.name, participant.deviceID);
|
||||||
|
activeParticipants.remove(suid);
|
||||||
|
}
|
||||||
|
conn.close(CloseFrame.NORMAL);
|
||||||
|
// this automatically calls disconnectUser through the MarvelousServer
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Method called exclusively from {@link MarvelousServer} on closed connection.
|
||||||
|
* @param conn
|
||||||
|
* @param closedByRemote
|
||||||
|
*/
|
||||||
void disconnectUser(WebSocket conn, boolean closedByRemote) {
|
void disconnectUser(WebSocket conn, boolean closedByRemote) {
|
||||||
// TODO: notify clients and such if the connection was in fact closed by the remote. Also remove participant
|
// TODO: notify clients and such if the connection was in fact closed by the remote. Also remove participant
|
||||||
synchronized (newUsers) {
|
synchronized (newUsers) {
|
||||||
|
Loading…
Reference in New Issue
Block a user