Hi,
can't pass validation with error message "The program ran too long and was closed!"
during debugging the program stops at line 23 in "server.java"
and code in line 25 not executed
where is the mistake?
Thanks.
package com.codegym.task.task30.task3008;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.SocketAddress;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.ConcurrentHashMap;
public class Server {
private static final Map<String, Connection> connectionMap = new ConcurrentHashMap<>();;
public static void main(String[] args) {
ConsoleHelper.writeMessage("input server port number:");
int port = ConsoleHelper.readInt();
try(ServerSocket serverSocket = new ServerSocket(port) ) {
ConsoleHelper.writeMessage("server started...");
while (true) {
Socket socket = serverSocket.accept();
// TODO: 22.09.2022 rem next line
System.out.println("socket accepted");
Handler handlerThread = new Handler(socket);
handlerThread.start();
}
} catch (IOException e) {
ConsoleHelper.writeMessage("An error occurred while starting or running the server.");
}
}
public static void sendBroadcastMessage(Message message){
for (Map.Entry<String, Connection> entry : connectionMap.entrySet()) {
try {
entry.getValue().send(message);
} catch (IOException e) {
ConsoleHelper.writeMessage("An error occurred while sending message to " + entry.getKey()+ ".");
}
}
}
private static class Handler extends Thread{
private final Socket socket;
public Handler (Socket socket){
super();
this.socket = socket;
}
private String serverHandshake(Connection connection) throws IOException, ClassNotFoundException {
connection.send(new Message(MessageType.NAME_REQUEST));
String userName = null;
while (true) {
Message message = connection.receive();
if (message != null && message.getType() == MessageType.USER_NAME
&& ( userName = message.getData()) != null && !userName.isEmpty()
&& !connectionMap.containsKey( userName)){
//Ok
connectionMap.put(userName, connection);
connection.send(new Message(MessageType.NAME_ACCEPTED));
return userName;
} else {
connection.send(new Message(MessageType.NAME_REQUEST));
}
}
}
private void notifyUsers(Connection connection, String userName) throws IOException {
for (Map.Entry<String, Connection> entry : connectionMap.entrySet()) {
if (!userName.equals(entry.getKey())){
Message message = new Message(MessageType.USER_ADDED, entry.getKey());
connection.send(message);
}
}
}
private void serverMainLoop(Connection connection, String userName) throws IOException, ClassNotFoundException{
while (true) {
Message message = connection.receive();
if (message.getType() == MessageType.TEXT) {
sendBroadcastMessage(new Message(MessageType.TEXT, userName + ": " + message.getData()));
} else {
ConsoleHelper.writeMessage("An error occurred, wrong message Type!");
}
}
}
@Override
public void run() {
String userName = null;
try (Connection connection = new Connection(socket)) {
SocketAddress address = connection.getRemoteSocketAddress();
ConsoleHelper.writeMessage("A new connection was established with a remote address " + address);
userName = serverHandshake(connection);
sendBroadcastMessage(new Message(MessageType.USER_ADDED, userName));
notifyUsers(connection, userName);
serverMainLoop(connection, userName);
} catch (IOException | ClassNotFoundException e) {
ConsoleHelper.writeMessage("An error occurred while communicating with the remote address");
} finally {
if (Objects.nonNull(userName)) {
connectionMap.remove(userName);
sendBroadcastMessage(new Message(MessageType.USER_REMOVED, userName));
}
ConsoleHelper.writeMessage("Connection with the remote address is closed");
}
}
}
}