有一台服务器被认为是同时为多个客户端服务。
因此,当客户端连接时,他将被添加到客户端阵列。当服务器收到消息时,它会发送给所有客户端。 当一个客户端连接时它完美地工作,但是当我同时有两个客户端时,消息只发送一次,之后它就不再起作用了。问题是什么?
服务器
static DataInputStream inputStream;
static DataOutputStream outputStream;
static ServerSocket serverSocket;
static final int PORT = 3003;
static Socket someClient;
static List<Socket> clients = new ArrayList<>();
public Server()
{
start();
}
public static void main(String[] args) throws IOException
{
try{
serverSocket = new ServerSocket(PORT);
print("Server started on " + serverSocket.getInetAddress().getHostAddress());
while (true)
{
someClient = serverSocket.accept();
new Server();
}
} catch (Exception e){
e.printStackTrace();
}
}
@Override
public void run()
{
try{
clients.add(someClient);
print("Connected from " + someClient.getInetAddress().getHostAddress());
InputStream sin = someClient.getInputStream();
OutputStream sout = someClient.getOutputStream();
inputStream = new DataInputStream(sin);
outputStream = new DataOutputStream(sout);
String message;
while (true)
{
message = inputStream.readUTF();
print(message);
for (int i = 0; i < clients.size(); i++)
{
Socket client = clients.get(i);
OutputStream os = client.getOutputStream();
DataOutputStream oss = new DataOutputStream(os);
oss.writeUTF(message);
}
}
} catch (Exception e){
e.printStackTrace();
}
}
客户端
socket = new Socket("0.0.0.0", 3003);
InputStream sin = socket.getInputStream();
OutputStream sout = socket.getOutputStream();
inputStream = new DataInputStream(sin);
outputStream = new DataOutputStream(sout);
sendButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if(key != null && key.length() == 16)
{
Date date = new Date();
String msg = ">> " + nickname + ": " + messageField.getText()+" | " + date.getHours()+":"+date.getMinutes()+"\n";
try {
outputStream.writeUTF(Encrypt.AESEncrypt(key, msg));
} catch (IOException e1) {
e1.printStackTrace();
}
messageField.setText("");
}
else if(key == null)
JOptionPane.showMessageDialog(J_Frame, "Your key field is empty");
else if(key.length() != 16)
JOptionPane.showMessageDialog(J_Frame, "Key's length should be 16 symbols");
}
});
while (true)
{
String message;
message = inputStream.readUTF();
append("\n" + Encrypt.AESDecrypt(key, message));
}
} catch (Exception e1) {
clear();
append(">> Unable to connect to the server.");
hideButtons();
}
答案 0 :(得分:1)
每次客户端连接到您的服务器时,它都会替换以前的连接:
while (true)
{
someClient = serverSocket.accept();
...
}
someClient
是静态的:
static Socket someClient;
表示所有线程共享它。 此外,对它的访问不会以任何方式同步,这意味着不保证其值的更改对其他线程可见。
在评论中指出Peter Lawrey,流也需要是非静态的:
static DataInputStream inputStream;
static DataOutputStream outputStream;
实际上,您总是从“最新”inputStream
中读取这一事实可能是您所描述行为的主要原因。
outputStream
似乎未被使用,因此最好将其删除。
除此之外,可能需要刷新OutputStreams
才能实际发送数据。