Я новичок в stackoverflow, и мне очень жаль, если подобный вопрос задают раньше, но я провел быстрый поиск и не смог найти ни одного заголовка, подобного моему. Я работаю над мультиклиентским приложением чата на Java. Я следил за обучающими материалами и могу отправлять сообщения, которые видит каждый пользователь в приложении. Но мне интересно, как создать и отправить личное сообщение пользователю spesifi c в чат.
import java.io.*;
import java.net.*;
import java.util.HashSet;
import java.util.Set;
public class ChatServer {
private int port;
private Set<String> userNames = new HashSet<>();
private Set<UserThread> userThreads = new HashSet<>();
public ChatServer(int port) {
this.port = port;
}
public static void main(String[] args) {
new ChatServer(9999).execute();
}
private void execute() {
try {
ServerSocket serverSocket = new ServerSocket(9999);
System.out.println("Server is running");
while (true) {
Socket socket = serverSocket.accept();
System.out.println("New user connected");
UserThread newUser = new UserThread(socket, this);
userThreads.add(newUser);
newUser.start();
}
} catch (IOException e) {
e.printStackTrace();
}
}
public void addUserName(String s) {
this.userNames.add(s);
}
public void broadcast(String serverMessage, UserThread excludeUser) {
for (UserThread aUser : userThreads) {
if (aUser != excludeUser)
aUser.sendMessage(serverMessage);
}
}
}
Приведенный выше код - это мой серверный код.
public void run() {
Console console = System.console();
String userName = console.readLine("Enter your username : ");
writer.println(userName);
String text;
do {
text = console.readLine("[" + userName + "]: ");
if (text.startsWith("[")) {
isTargeted = true;
this.aimUserName = text.substring(text.indexOf("[") + 1, text.indexOf("]"));
//System.out.println("Private Message to: " + aimUserName);
} else {
isTargeted = false;
}
writer.println(text);
} while (!text.equals("bye"));
try {
socket.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
, и этот код выше является частью моего класса потока записи. Как видите, если сообщение начинается с части «[имя]», «имя» означает пользователя, которому мы хотим отправить личное сообщение. Таким образом я могу получить имя пользователя, которому хочу отправить личное сообщение, но я не мог понять, как передать это сообщение только этому пользователю spesifi c. Я считаю, что мне нужно настроить функцию трансляции в классе ChatServer, но я действительно не знаю, как это сделать. Какие шаги мне следует выполнить?
- Изменить -
Я работал над своим вопросом и сделал некоторые дополнения для решения моей проблемы. Прежде всего, я думаю, что должен поделиться с вами всем, что у меня есть. Ранее я поделился своим классом ChatServer. Другие классы, которые у меня есть:
import java.io.IOException;
import java.net.Socket;
public class ChatClient {
public static void main(String[] args) {
new ChatClient().execute();
}
private void execute() {
try {
Socket socket = new Socket("localhost", 3);
System.out.println("Connected to chat server");
new ReadThread(socket, this).start();
new WriteThread(socket, this).start();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
import java.net.*;
import java.io.*;
public class ReadThread extends Thread{
private BufferedReader reader;
private Socket socket;
private ChatClient client;
public ReadThread(Socket socket, ChatClient client) {
this.socket = socket;
this.client = client;
InputStream input;
try {
input = this.socket.getInputStream();
this.reader = new BufferedReader(new InputStreamReader(input));
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void run() {
while(true) {
try {
String response = this.reader.readLine();
System.out.println("\n" + response);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
break;
}
}
}
}
import java.net.Socket;
import java.io.*;
public class UserThread extends Thread {
private Socket socket;
private ChatServer server;
PrintWriter writer = null;
public String userName;
public UserThread(Socket socket, ChatServer chatServer) {
this.socket = socket;
this.server = chatServer;
}
public void run() {
try {
InputStream input = socket.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(input));
OutputStream output = socket.getOutputStream();
writer = new PrintWriter(output,true);
String userName = reader.readLine();
this.userName = userName;
server.addUserName(userName);
String serverMessage = "New user connected: " + userName;
server.broadcast(serverMessage,this);
String clientMessage;
do {
clientMessage = reader.readLine();
serverMessage = "[" + userName + "] : " + clientMessage;
server.broadcast(serverMessage, this);
}while(!clientMessage.equals("bye"));
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void sendMessage(String serverMessage) {
writer.println(serverMessage);
}
}
import java.net.*;
import java.io.*;
public class WriteThread extends Thread {
private Socket socket;
private ChatClient client;
private PrintWriter writer;
public WriteThread(Socket socket, ChatClient client) {
this.socket = socket;
this.client = client;
OutputStream output;
try {
output = socket.getOutputStream();
this.writer = new PrintWriter(output, true);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void run() {
Console console = System.console();
String userName = console.readLine("Enter your username : ");
writer.println(userName);
String text;
do {
text = console.readLine("[" + userName + "]: ");
if(text.startsWith("[")){
String aimUserName = text.substring(text.indexOf("[")+1,text.indexOf("]"));
System.out.println("Private Message to: " + aimUserName);}
writer.println(text);
}while(!text.equals("bye"));
/*do {
text = console.readLine("[" + userName + "]: ");
writer.println(text);
}while(!text.equals("bye"));*/
try {
socket.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
Эти коды работают правильно, и я могу очень аккуратно общаться в мульти-чате. Но во время работы над личным чатом я добавил в ChatServer строку:
public void privatebr(String serverMessage, String targetUserName){
for(UserThread aUser: userThreads){
if(aUser.userName == targetUserName)
aUser.sendMessage(serverMessage);
}
в UserThread, я отредактировал часть как:
String clientMessage;
do {
clientMessage = reader.readLine();
serverMessage = "[" + userName + "] : " + clientMessage;
if(clientMessage.startsWith("[")){
String targetUserName = clientMessage.substring(clientMessage.indexOf("[")+1,clientMessage.indexOf("]"));
serverMessage = "[" + userName + "] : " + clientMessage;
server.privatebr(serverMessage, targetUserName);
}else{
server.broadcast(serverMessage, this);
}
}while(!clientMessage.equals("bye"));
Но когда я сделал все эти правки нарушили нормальный ход мульти-чата, в чем моя вина? Почему все сломалось?