我编写了一个监听客户端消息的服务器,它是 http://docs.oracle.com/javase/tutorial/networking/sockets/clientServer.html 的变体。我在 eclipse 中将它们作为同一项目中的 java 类编写。为了测试它,我有一个带有 main 的客户端类,该类启动服务器然后向其发送消息。当我运行它时,程序只是卡在 serverSocket.accept(); 处。根据ServerSocket接受的javadoc不是异步的?这可以解释挂起的情况,但是教程代码是如何工作的呢?
更新 - 这是我的工作代码: 这是工作代码:
MyServer.java
/*imports neglected for brevity */
public class MyServer {
public static final String hostname = "localhost";
public static final int portNum = 4444;
ServerSocket serverSocket;
BufferedReader serverReader;
File serverLog;
FileWriter fw;
BufferedWriter serverWriter;
Socket clientSocket;
public static void main(String[] args) {
MyServer server = new MyServer(portNum);
// start the server so it can listen to client messages
server.start();
}
public MyServer(int portNum) {
try {
// endpt for server side, used to listen for client socket
serverSocket = new ServerSocket(portNum);
/* have server socket listen for connection, return client socket.
* serverSocket can now talk to clientSocket
*/
clientSocket = serverSocket.accept();
// server writes messages to this log
serverLog = new File("ServerLog.txt");
if(!serverLog.exists())
serverLog.createNewFile();
fw = new FileWriter(serverLog.getAbsoluteFile());
serverWriter = serverWriter = new BufferedWriter(fw);
/* server reads from this stream that is populated by the client's
* OUTPUT stream/client socket's INPUT stream
*/
serverReader = new BufferedReader(
new InputStreamReader(clientSocket.getInputStream())
);
}
catch (Exception e) {
e.printStackTrace();
}
}
public void start() {
String clientMsg;
try {
while((clientMsg = serverReader.readLine()) != null) {
if(clientMsg.startsWith("exit")) {
break;
}
serverWriter.append(clientMsg);
}
serverWriter.flush();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
MyClient.java 公共(public)类 MyClient { 公共(public)静态最终字符串主机名=“localhost”; 公共(public)静态最终 int portNum = 4444;
public static void main(String[] args) {
String msg = "message 1";
try {
// server is listening on http://localhost:4444
Socket serversSocket = new Socket(hostname, portNum);
PrintWriter clientOut = new PrintWriter(serversSocket.getOutputStream(), true);
// send first message
clientOut.println(msg);
msg = "message 2";
// send second message
clientOut.println(msg);
msg = "exit";
// this will stop the server
clientOut.println(msg);
}
catch (Exception e) {
e.printStackTrace();
}
}
}
最佳答案
如果您完成本教程,它会创建两个应用程序,一个带有客户端,一个带有服务器。
您不能创建这样的变体,因为当您调用构造函数时,整个应用程序会在 clientSocket = serverSocket.accept();
中阻塞。
如果您出于某种原因坚持创建单个应用程序,则可以进行多线程处理。但我看不出您有任何理由要这样做。
关于java - 测试客户端服务器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22263389/