Fix: TCP Reconnection system -> model too

This commit is contained in:
rubenpirreram
2026-05-10 18:59:49 +02:00
parent f9fa12ac64
commit 670afb40a8
7 changed files with 107 additions and 127 deletions
@@ -1,33 +0,0 @@
package it.polimi.ingsw.gc14.Network.NetworkEvents;
import it.polimi.ingsw.gc14.Controller.GameController;
import it.polimi.ingsw.gc14.Network.EventType;
import it.polimi.ingsw.gc14.Network.NetworkEvent;
import java.io.Serializable;
/**
* NetworkEvent to avoid drawing a card from the lower card list
*/
public class SkipPlayerDisconnected extends NetworkEvent implements Serializable{
/**
* Class constructor.
* Initializes all the attributes.
* @param username the name of the player requesting the event
*/
public SkipPlayerDisconnected(String username){
super(username, EventType.SKIP_PLAYER_DISCONNECTED, false);
}
/**
* @param gameController the Game Controller on which to apply the event
* @return true if the player could skipTheTurn, false otherwise
*/
@Override
public boolean apply(GameController gameController){
return gameController.SkipNotConnectedPlayer(username);
}
}
@@ -3,7 +3,7 @@ package it.polimi.ingsw.gc14.Network.RMI.Server;
import it.polimi.ingsw.gc14.LimitedMap;
import it.polimi.ingsw.gc14.Model.Game;
import it.polimi.ingsw.gc14.Network.NetworkEvent;
import it.polimi.ingsw.gc14.Network.NetworkEvents.SkipPlayerDisconnected;
import it.polimi.ingsw.gc14.Network.NetworkEvents.DisconnectedPlayer;
import java.util.Map;
import java.util.concurrent.*;
@@ -21,7 +21,7 @@ import java.util.concurrent.*;
* <li>stops the watchdog;</li>
* <li>marks the player as offline in {@code playerList};</li>
* <li>removes the callback from {@code clients};</li>
* <li>optionally pushes a {@link SkipPlayerDisconnected} event if it was that
* <li>optionally pushes a {@link DisconnectedPlayer} event if it was that
* player's turn.</li>
* </ul>
*/
@@ -104,7 +104,7 @@ public class RMIHeartbeat {
Game snapshot = this.game;
if (snapshot != null &&
snapshot.getCurrentState().getCurrentPlayer().getUserName().equals(username)) {
actionQueue.add(new SkipPlayerDisconnected(username));
actionQueue.add(new DisconnectedPlayer(username));
}
System.out.println("RMI disconnected: " + username);
@@ -3,7 +3,7 @@ package it.polimi.ingsw.gc14.Network.TCP.Server;
import it.polimi.ingsw.gc14.LimitedMap;
import it.polimi.ingsw.gc14.Model.Game;
import it.polimi.ingsw.gc14.Network.NetworkEvent;
import it.polimi.ingsw.gc14.Network.NetworkEvents.SkipPlayerDisconnected;
import it.polimi.ingsw.gc14.Network.NetworkEvents.DisconnectedPlayer;
import java.io.*;
import java.net.*;
@@ -133,9 +133,7 @@ public class ClientHandler implements Runnable {
running = false;
clientHandlers.remove(this);
limitedMap.put(username, false);
if(this.game!=null && this.game.getCurrentState().getCurrentPlayer().getUserName().equals(username)) {
actionQueue.add(new SkipPlayerDisconnected(username));
}
actionQueue.add(new DisconnectedPlayer(username));
System.out.println("Disconnected player: " + username);
try { clientSocket.close(); } catch (IOException ignored) {}
}
@@ -3,6 +3,7 @@ package it.polimi.ingsw.gc14.Network.TCP.Server;
import it.polimi.ingsw.gc14.Controller.GameController;
import it.polimi.ingsw.gc14.LimitedMap;
import it.polimi.ingsw.gc14.Model.Game;
import it.polimi.ingsw.gc14.Model.Player;
import it.polimi.ingsw.gc14.Network.ClientPlayer;
import it.polimi.ingsw.gc14.Network.EventType;
import it.polimi.ingsw.gc14.Network.NetworkEvent;
@@ -29,7 +30,7 @@ public class TCPServer {
ServerSocket socketTCP;
ServerSocket heartbeatSocketTCP; // ← nuovo ServerSocket
GameController controller;
final GameController controller;
BlockingQueue<NetworkEvent> actionQueue;
LimitedMap<String, Boolean> playerList;
List<ClientHandler> clientHandlers;
@@ -88,57 +89,66 @@ public class TCPServer {
continue;
}
if (playerList.isEmpty()) {
if(controller.getModel() == null){
Game model = new Game(eventAddPlayer.getProposedNPlayer());
controller.setModel(model);
playerList.setLimit(eventAddPlayer.getProposedNPlayer());
}
}
String username = eventAddPlayer.getUsername();
if (controller.addPlayer(username)) {
// nuovo giocatore
playerList.put(username, true);
System.out.println("Accepted player: " + username);
ClientHandler handler = new ClientHandler(
username, clientSocket, clientSend, clientReceive,
clientHandlers,playerList, actionQueue
);
clientSocket.getOutputStream().write(1);
pendingHeartbeat.put(username, handler);
Thread thread = new Thread(handler);
thread.start();
clientHandlers.add(handler);
connectedPlayers++;
// metti in attesa del socket heartbeat
synchronized (controller) {
if (playerList.isEmpty()) {
if(controller.getModel() == null){
Game model = new Game(eventAddPlayer.getProposedNPlayer());
controller.setModel(model);
playerList.setLimit(eventAddPlayer.getProposedNPlayer());
}
else
{
for(Player p:controller.getModel().getPlayers()) {
playerList.put(p.getUserName(),false);
}
}
}
}
else if(playerList.containsKey(username) && !playerList.get(username)){
// riconnessione
playerList.put(username, true);
System.out.println("Reconnected player: " + username);
String username = eventAddPlayer.getUsername();
ClientHandler handler = new ClientHandler(
username, clientSocket, clientSend, clientReceive,
clientHandlers, playerList, actionQueue
);
clientSocket.getOutputStream().write(1);
pendingHeartbeat.put(username, handler);
handler.notifyModel(controller.getModel());
Thread thread = new Thread(handler);
thread.start();
clientHandlers.add(handler);
connectedPlayers++;
actionQueue.add(new ReconnectPlayer(username));
}
else{
clientSocket.getOutputStream().write(-1);
clientSocket.close();
System.out.println("Player could not be added. Connection terminated.");
}
if (controller.addPlayer(username)) {
// nuovo giocatore
playerList.put(username, true);
System.out.println("Accepted player: " + username);
ClientHandler handler = new ClientHandler(
username, clientSocket, clientSend, clientReceive,
clientHandlers,playerList, actionQueue
);
clientSocket.getOutputStream().write(1);
pendingHeartbeat.put(username, handler);
Thread thread = new Thread(handler);
thread.start();
clientHandlers.add(handler);
connectedPlayers++;
// metti in attesa del socket heartbeat
}
else if(playerList.containsKey(username) && !playerList.get(username)){
// riconnessione
playerList.put(username, true);
System.out.println("Reconnected player: " + username);
ClientHandler handler = new ClientHandler(
username, clientSocket, clientSend, clientReceive,
clientHandlers, playerList, actionQueue
);
clientSocket.getOutputStream().write(1);
pendingHeartbeat.put(username, handler);
handler.notifyModel(controller.getModel());
Thread thread = new Thread(handler);
thread.start();
clientHandlers.add(handler);
connectedPlayers++;
actionQueue.add(new ReconnectPlayer(username));
}
else{
clientSocket.getOutputStream().write(-1);
clientSocket.close();
System.out.println("Player could not be added. Connection terminated.");
}
}
}