Java中如何重放传入请求?ServerSocket响应无返回问题求助
问题原因梳理
- 逻辑阻塞:
while ((s = in.readLine()) != null)只有在客户端主动断开输入流时才会返回null跳出循环,你当前的写法会一直卡在循环中,后续的响应写入、文件写入逻辑永远不会执行 - 缓冲区未输出:
PrintWriter开启的自动flush仅对println()、printf()、format()方法生效,你调用的out.write()不会触发自动flush,数据滞留在本地缓冲区没有发送到网络 - 语法错误:Java字符串中正则的
\s需要转义为\\s,且ss变量未提前声明,代码无法正常编译 - 边界异常风险:如果收到的内容不包含
PUSH前缀,split返回的数组长度不足会触发数组越界异常 - 资源未释放:socket、流使用完成后未主动关闭,容易出现资源泄漏、数据残留问题
修正后代码
import org.apache.commons.io.FileUtils; import java.io.*; import java.net.ServerSocket; import java.net.Socket; public class SocketServerDemo { public static void main(String[] args) { ServerSocket server = null; Socket client = null; PrintWriter out = null; BufferedReader in = null; String pathToRReq = "你的文件存储路径"; try { server = new ServerSocket(4321); client = server.accept(); out = new PrintWriter(client.getOutputStream(), true); in = new BufferedReader(new InputStreamReader(client.getInputStream())); // 发送启动提示 String initMsg = "SERVER: Started."; out.println(initMsg); String s; String[] ss = null; // 匹配到PUSH开头的内容就停止读取,不需要等客户端断开连接 while ((s = in.readLine()) != null) { System.out.println("RECV: " + s); if (s.startsWith("PUSH ")) { ss = s.split("PUSH\\s"); break; } } // 避免空指针和数组越界 if (ss != null && ss.length > 0) { FileUtils.writeStringToFile(new File(pathToRReq), ss[0], "UTF-8"); // 写入响应后手动flush,确保数据发送到网络 out.write("Some text"); out.flush(); System.out.println(ss[0]); } else { out.write("Invalid request"); out.flush(); } } catch (Exception e) { e.printStackTrace(); } finally { // 统一释放资源,关闭时也会触发缓冲区flush try { if (in != null) in.close(); if (out != null) out.close(); if (client != null) client.close(); if (server != null) server.close(); } catch (IOException e) { e.printStackTrace(); } } } }
补充说明
- 如果对接的是HTTP协议的客户端,需要按照HTTP规范返回响应(包含状态行、响应头、空行、响应体),否则客户端会识别为非法响应
- 如果需要支持多客户端同时连接,需要将单个客户端的处理逻辑放到独立线程中,避免ServerSocket阻塞无法接收新连接
- 如果你的业务需要读取完整的请求体再返回响应,需要提前约定请求结束标识(比如空行、特定长度标识),不要等待流断开再处理逻辑
内容的提问来源于stack exchange,提问作者bpm2021
相关产品推荐
相关产品推荐

