How to interrupt BufferedReader's readLine

后端 未结 9 1436
醉梦人生
醉梦人生 2020-11-29 07:56

I am trying to read input from a socket line by line in multiple threads. How can I interrupt readLine() so that I can gracefully stop the thread that it\'s bl

9条回答
  •  余生分开走
    2020-11-29 08:27

    If you want to use readLine on a server socket within a client-server tcp architecture, for instance, you can use setSoTimeout(int timeout) of java.net.Socket.

    From the Socket#setSoTimeout(int timeout) Documentation:

    Enable/disable SO_TIMEOUT with the specified timeout, in milliseconds. With this option set to a non-zero timeout, a read() call on the InputStream associated with this Socket will block for only this amount of time. If the timeout expires, a java.net.SocketTimeoutException is raised, though the Socket is still valid.

    public class MainApp {
        public static void main(String[] args) throws Exception {
            ExecutorService executorService = Executors.newFixedThreadPool(10);
            ServerSocket serverSocket = new ServerSocket(11370);
            Socket clientSocket = serverSocket.accept();
            clientSocket.setSoTimeout(2000);
            executorService.execute(new ReadingThread(clientSocket));
            // ... some async operations
            executorService.shutdown();
        }
    }
    
    public class ReadingThread implements Runnable {
        private final Socket clientSocket;
        public ReadingThread(Socket clientSocket) {
            this.clientSocket = clientSocket;
        }
    
        @Override
        public void run() {
            BufferedReader socketReader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
            String readInput = null;
            while (!Thread.currentThread().isInterrupted()) {
                try {
                    readInput = socketReader.readLine();
                } catch (SocketTimeoutException e) {
                    continue; 
                }
            }
            // operations with readInput
        }
    }
    

    The main application implements a server socket which listens to connections and has a thread pool. If an incoming client communication is accepted, then a new Thread from the pool is assigned and the run function is invoked in ReadingThread (can be adjusted to allow multiple threads). On the socket used for communicating to the client the property setSoTimeout(int timeout) has been set. Therefore if readLine does not return within the specified timeout a SocketTimeoutException is thrown. You can check in a loop whether the ReadingThread has been interrupted by the main application, and if so stop reading from the socket.

提交回复
热议问题