forked from AdvancedProgramming1404/WS-09-Network
init project
This commit is contained in:
@@ -0,0 +1,17 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<groupId>org.example</groupId>
|
||||
<artifactId>chat-app</artifactId>
|
||||
<version>1.0-SNAPSHOT</version>
|
||||
|
||||
<properties>
|
||||
<maven.compiler.source>21</maven.compiler.source>
|
||||
<maven.compiler.target>21</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
</project>
|
||||
@@ -0,0 +1,72 @@
|
||||
package chat;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStreamReader;
|
||||
import java.io.PrintWriter;
|
||||
import java.net.Socket;
|
||||
|
||||
public class ChatClient {
|
||||
|
||||
private final String host;
|
||||
private final int port;
|
||||
private Socket socket;
|
||||
private PrintWriter out;
|
||||
private BufferedReader in;
|
||||
private BufferedReader consoleReader;
|
||||
|
||||
public ChatClient(String host, int port) {
|
||||
this.host = host;
|
||||
this.port = port;
|
||||
this.consoleReader = new BufferedReader(new InputStreamReader(System.in));
|
||||
}
|
||||
|
||||
public void start() {
|
||||
try {
|
||||
connectToServer();
|
||||
MessageListener messageListener = new MessageListener(in);
|
||||
Thread listenerThread = new Thread(messageListener);
|
||||
listenerThread.setDaemon(true);
|
||||
listenerThread.start();
|
||||
readUserInputAndSend();
|
||||
} catch (IOException e) {
|
||||
System.err.println("Client error: " + e.getMessage());
|
||||
} finally {
|
||||
cleanup();
|
||||
}
|
||||
}
|
||||
|
||||
private void connectToServer() throws IOException {
|
||||
// TODO: create socket connection to host:port
|
||||
// TODO: initialize output stream (PrintWriter)
|
||||
// TODO: initialize input stream (BufferedReader)
|
||||
}
|
||||
|
||||
private void readUserInputAndSend() throws IOException {
|
||||
// TODO: read continuously from console
|
||||
// TODO: send each input line to server
|
||||
}
|
||||
|
||||
private void cleanup() {
|
||||
// TODO: close socket safely
|
||||
// TODO: release resources
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
String host = "127.0.0.1";
|
||||
int port = 12345;
|
||||
|
||||
if (args.length > 0) {
|
||||
host = args[0];
|
||||
}
|
||||
if (args.length > 1) {
|
||||
try {
|
||||
port = Integer.parseInt(args[1]);
|
||||
} catch (NumberFormatException e) {
|
||||
System.err.println("Invalid port. Using default: " + port);
|
||||
}
|
||||
}
|
||||
|
||||
new ChatClient(host, port).start();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,69 @@
|
||||
package chat;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.net.ServerSocket;
|
||||
import java.net.Socket;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
|
||||
public class ChatServer {
|
||||
|
||||
private final int port;
|
||||
private final Set<ClientHandler> connectedClients;
|
||||
private final ExecutorService threadPool;
|
||||
|
||||
public ChatServer(int port) {
|
||||
this.port = port;
|
||||
this.connectedClients = Collections.synchronizedSet(new HashSet<>());
|
||||
this.threadPool = Executors.newCachedThreadPool();
|
||||
}
|
||||
|
||||
public void start() {
|
||||
try (ServerSocket serverSocket = new ServerSocket(port)) {
|
||||
System.out.println("Chat server started on port " + port);
|
||||
|
||||
while (true) {
|
||||
Socket clientSocket = serverSocket.accept();
|
||||
ClientHandler clientHandler = new ClientHandler(clientSocket, this);
|
||||
connectedClients.add(clientHandler);
|
||||
threadPool.execute(clientHandler);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
System.err.println("Server error: " + e.getMessage());
|
||||
} finally {
|
||||
threadPool.shutdown();
|
||||
}
|
||||
}
|
||||
|
||||
public void broadcast(String message, ClientHandler sender) {
|
||||
// step 1: iterate through connectedClients safely
|
||||
// step 2: skip the sender client
|
||||
// step 3: send message to remaining clients using sendMessage
|
||||
}
|
||||
|
||||
public void broadcastSystemMessage(String message) {
|
||||
// step 1: iterate through all connected clients
|
||||
// step 2: send system message to each client
|
||||
}
|
||||
|
||||
public void removeClient(ClientHandler clientHandler) {
|
||||
// step 1: remove client from connectedClients set
|
||||
// step 2: retrieve username from clientHandler
|
||||
// step 3: broadcast system message about user leaving
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
int port = 12345;
|
||||
if (args.length > 0) {
|
||||
try {
|
||||
port = Integer.parseInt(args[0]);
|
||||
} catch (NumberFormatException e) {
|
||||
System.err.println("Invalid port. Using default: " + port);
|
||||
}
|
||||
}
|
||||
new ChatServer(port).start();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,78 @@
|
||||
package chat;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStreamReader;
|
||||
import java.io.PrintWriter;
|
||||
import java.net.Socket;
|
||||
|
||||
public class ClientHandler implements Runnable {
|
||||
|
||||
private final Socket clientSocket;
|
||||
private final ChatServer chatServer;
|
||||
private PrintWriter out;
|
||||
private BufferedReader in;
|
||||
private String username;
|
||||
|
||||
public ClientHandler(Socket clientSocket, ChatServer chatServer) {
|
||||
this.clientSocket = clientSocket;
|
||||
this.chatServer = chatServer;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
setupStreams();
|
||||
requestUsername();
|
||||
announceJoin();
|
||||
listenForMessages();
|
||||
} catch (IOException e) {
|
||||
System.err.println("Client handler error: " + e.getMessage());
|
||||
} finally {
|
||||
cleanup();
|
||||
}
|
||||
}
|
||||
|
||||
private void setupStreams() throws IOException {
|
||||
out = new PrintWriter(clientSocket.getOutputStream(), true);
|
||||
in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
|
||||
}
|
||||
|
||||
private void requestUsername() throws IOException {
|
||||
out.println("Enter your username:");
|
||||
username = in.readLine();
|
||||
if (username == null || username.trim().isEmpty()) {
|
||||
username = "Anonymous";
|
||||
}
|
||||
}
|
||||
|
||||
private void announceJoin() {
|
||||
chatServer.broadcastSystemMessage("[System] " + username + " joined the chat.");
|
||||
}
|
||||
|
||||
private void listenForMessages() throws IOException {
|
||||
String message;
|
||||
while ((message = in.readLine()) != null) {
|
||||
chatServer.broadcast(username + ": " + message, this);
|
||||
}
|
||||
}
|
||||
|
||||
private void cleanup() {
|
||||
chatServer.removeClient(this);
|
||||
try {
|
||||
if (clientSocket != null && !clientSocket.isClosed()) {
|
||||
clientSocket.close();
|
||||
}
|
||||
} catch (IOException e) {
|
||||
System.err.println("Error closing socket: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public void sendMessage(String message) {
|
||||
out.println(message);
|
||||
}
|
||||
|
||||
public String getUsername() {
|
||||
return username;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
package chat;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.IOException;
|
||||
|
||||
public class MessageListener implements Runnable {
|
||||
|
||||
private final BufferedReader inputReader;
|
||||
|
||||
public MessageListener(BufferedReader inputReader) {
|
||||
this.inputReader = inputReader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
// TODO: continuously read messages from server
|
||||
// TODO: print received messages immediately
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user