WangHan
2024-09-12 d5855a4926926698b740bc6c7ba489de47adb68b
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
package tech.powerjob.common.utils.net;
 
import lombok.extern.slf4j.Slf4j;
import tech.powerjob.common.utils.CommonUtils;
 
import java.io.IOException;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
 
/**
 * 简易服务器
 *
 * @author tjq
 * @since 2024/2/8
 */
@Slf4j
public class PingPongSocketServer implements PingPongServer {
 
    private Thread thread;
 
    private ServerSocket serverSocket;
 
    private volatile boolean terminated = false;
 
    @Override
    public void initialize(int port) throws Exception{
        serverSocket = new ServerSocket(port);
 
        thread = new Thread(() -> {
            while (true) {
                if (terminated) {
                    return;
                }
                // 接收连接,如果没有连接,accept() 方法会阻塞
                try (Socket socket = serverSocket.accept();OutputStream outputStream = socket.getOutputStream();) {
 
                    socket.setSoTimeout(2000);
                    socket.setKeepAlive(false);
 
                    outputStream.write(PingPongUtils.PONG.getBytes(StandardCharsets.UTF_8));
                    // BufferedReader.readLine() 会等待直到遇到换行符(\n)或回车符(\r\n),才会返回一行内容。如果服务器发送的数据没有这些换行符,readLine() 会一直阻塞,直到超时
                    outputStream.write(System.lineSeparator().getBytes(StandardCharsets.UTF_8));
                    outputStream.flush();
                } catch (Exception e) {
                    if (!terminated) {
                        log.warn("[PingPongSocketServer] process accepted socket failed!", e);
                    }
                }
            }
        }, "PingPongSocketServer-Thread");
 
        thread.start();
    }
 
    @Override
    public void close() throws IOException {
        terminated = true;
        CommonUtils.executeIgnoreException(() -> serverSocket.close());
        thread.interrupt();
    }
}