最近在學Java的NIO編程,學習過程中編寫了一個Demo,特此記錄。
- 代碼目錄結構:
-
代碼描述: 使用ThreadPool啟動十個客戶端線程模擬十個請求,並與服務端保持長連接。每個客戶端每隔3秒向服務端發送數據,服務端監聽客戶端的連接和可讀事件,並輸出客戶端內容。半分鍾過后線程池強制中斷客戶端線程,客戶端關閉與服務端的連接,服務端監聽客戶端的關閉,並將相應事件從selector中取消。
- 客戶端代碼內容:
NioClient.java 主線程,啟動客戶端程序。
1 package com.vincent.fat.core.nio.client; 2 3 4 import java.util.concurrent.ExecutorService; 5 import java.util.concurrent.Executors; 6 import java.util.concurrent.TimeUnit; 7 import java.util.concurrent.atomic.AtomicLong; 8 9 public class NioClient { 10 private static final ExecutorService executor = Executors.newCachedThreadPool(); 11 private static final AtomicLong countSend=new AtomicLong(0L); 12 public static void main(String[] args) throws InterruptedException { 13 clientStart(); 14 } 15 public static void clientStart() throws InterruptedException { 16 OnlyNosClients(); 17 } 18 19 private static void OnlyNosClients() throws InterruptedException { 20 for (int i = 0; i < 10; i++) { 21 executor.submit( 22 new RequestRemoteServerWithTcp("localhost",17899,countSend) 23 ); 24 } 25 //10秒鍾后中斷所有線程 26 TimeUnit.SECONDS.sleep(10); 27 executor.shutdownNow(); 28 } 29 30 private static void startNewClients() { 31 while (!Thread.currentThread().isInterrupted()) 32 { 33 executor.submit( 34 new RequestRemoteServerWithTcp("localhost",17899,countSend) 35 ); 36 } 37 } 38 }
RequestRemoteServerWithTcp.java 客戶端啟動代碼
其中 com.github.javafaker.Faker 是用來生成隨機數據的類,org.slf4j.Logger 是用於日志輸出的類
1 package com.vincent.fat.core.nio.client; 2 3 import com.github.javafaker.Faker; 4 import org.slf4j.Logger; 5 import org.slf4j.LoggerFactory; 6 7 import java.io.IOException; 8 import java.net.InetSocketAddress; 9 import java.net.SocketAddress; 10 import java.nio.ByteBuffer; 11 import java.nio.channels.SocketChannel; 12 import java.nio.charset.StandardCharsets; 13 import java.util.Locale; 14 import java.util.Objects; 15 import java.util.concurrent.TimeUnit; 16 import java.util.concurrent.atomic.AtomicLong; 17 18 public class RequestRemoteServerWithTcp implements Runnable { 19 public static final Logger logger = LoggerFactory.getLogger(RequestRemoteServerWithTcp.class); 20 public static final Locale locale=Locale.SIMPLIFIED_CHINESE; 21 public static final Faker faker =new Faker(locale); 22 private final String serverAddress; 23 private final int serverPoint; 24 private int localPoint; 25 private final AtomicLong countSend ; 26 public RequestRemoteServerWithTcp(String serverAddress,int serverPoint,AtomicLong countSend){ 27 this.serverAddress=serverAddress; 28 this.serverPoint=serverPoint; 29 this.countSend=countSend; 30 } 31 /** 32 * When an object implementing interface <code>Runnable</code> is used 33 * to create a thread, starting the thread causes the object's 34 * <code>run</code> method to be called in that separately executing 35 * thread. 36 * <p> 37 * The general contract of the method <code>run</code> is that it may 38 * take any action whatsoever. 39 * 40 * @see Thread#run() 41 */ 42 @Override 43 public void run() { 44 try { 45 this.doRequest(); 46 } catch (IOException ioException) { 47 ioException.printStackTrace(); 48 } 49 } 50 private void doRequest() throws IOException { 51 SocketChannel socketChannel = null; 52 try { 53 socketChannel = SocketChannel.open(new InetSocketAddress(this.serverAddress,this.serverPoint)); 54 socketChannel.configureBlocking(false); 55 SocketAddress localAddress = socketChannel.getLocalAddress(); 56 while(!socketChannel.isConnected()){} 57 logger.debug("[{}]完成連接",socketChannel.getLocalAddress()); 58 this.localPoint = ((InetSocketAddress) socketChannel.getLocalAddress()).getPort(); 59 while (!Thread.currentThread().isInterrupted()) 60 { 61 ByteBuffer buffer = this.prepareData(this.localPoint); 62 socketChannel.write(buffer); 63 buffer.clear(); 64 long currentSendCount = this.countSend.incrementAndGet(); 65 logger.info("客戶端[{}]的第【{}】條數據發送完成",localAddress,currentSendCount); 66 TimeUnit.SECONDS.sleep(3); 67 ByteBuffer readBuffer = ByteBuffer.allocate(2*1024); 68 getResponseData(socketChannel, readBuffer); 69 } 70 } catch (IOException ioException) { 71 logger.error("ioException:",ioException); 72 }catch (Exception e) 73 { 74 logger.error("端口為{}的客戶端報錯",this.localPoint,e); 75 }finally { 76 if (!Objects.isNull(socketChannel)&&socketChannel.isOpen()) 77 { 78 //關閉輸出通道 79 socketChannel.shutdownOutput(); 80 socketChannel.shutdownInput(); 81 socketChannel.close(); 82 logger.info("【{}】的輸出通道關閉!",this.localPoint); 83 } 84 } 85 86 } 87 88 private void getResponseData(SocketChannel socketChannel, ByteBuffer readBuffer) throws IOException { 89 //接收客戶端數據 90 int readBytes = 0; 91 StringBuilder content = new StringBuilder(); 92 while ((readBytes=socketChannel.read(readBuffer))>0) { 93 //處理數據 94 content.append(new String(readBuffer.array(), StandardCharsets.UTF_8)); 95 readBuffer.clear(); 96 } 97 //判斷服務端斷開連接 98 //當服務端沒有斷開連接的時候readBytes=0這樣保持長連接 99 //當服務端斷開連接的時候readBytes=-1 100 if (readBytes<0) 101 { 102 logger.debug("服務端斷開連接....."); 103 socketChannel.close(); 104 } 105 //處理數據 106 else { 107 logger.info("收到的內容是: <{}>", 108 content.toString()); 109 } 110 } 111 112 private ByteBuffer prepareData(int channelPoint) { 113 StringBuilder name =new StringBuilder(faker.university().name()); 114 name.insert(0,(channelPoint+"==========>")); 115 return ByteBuffer.wrap(name.toString().getBytes(StandardCharsets.UTF_8)); 116 } 117 }
服務端代碼:NioServer.java
1 package com.vincent.fat.core.nio.server; 2 3 import cn.hutool.core.util.RandomUtil; 4 import org.slf4j.Logger; 5 import org.slf4j.LoggerFactory; 6 7 import java.io.IOException; 8 import java.net.InetSocketAddress; 9 import java.nio.ByteBuffer; 10 import java.nio.channels.*; 11 import java.nio.charset.StandardCharsets; 12 import java.util.Iterator; 13 import java.util.Objects; 14 import java.util.Set; 15 import java.util.concurrent.*; 16 import java.util.concurrent.atomic.AtomicInteger; 17 18 public class NioServer { 19 public static final Logger logger = LoggerFactory.getLogger(NioServer.class); 20 private static final Long TIME_OUT= 3000L; 21 private static final BlockingQueue<Future<String>> futureQueue =new LinkedBlockingQueue<>(); 22 private static final AtomicInteger selectorNos=new AtomicInteger(0); 23 private static final AtomicInteger handleDataNo=new AtomicInteger(0); 24 private static final AtomicInteger resDataNo=new AtomicInteger(0); 25 public static void main(String[] args) throws IOException, InterruptedException { 26 startServer(args); 27 } 28 public static void startServer(String[] args) throws IOException, InterruptedException { 29 //新建channel 30 ServerSocketChannel serverSocketChannel =ServerSocketChannel.open(); 31 //設置服務端屬性,為非阻塞模式 32 serverSocketChannel.configureBlocking(false); 33 //綁定服務端端口 34 serverSocketChannel.bind(new InetSocketAddress(17899)); 35 //新建selector 36 Selector selector = Selector.open(); 37 //注冊channel到selector 38 serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT); 39 logger.debug("服務在[{}]啟動成功,正在監聽事件。。。。。",serverSocketChannel.getLocalAddress()); 40 //while循環監聽事件 41 while (!Thread.currentThread().isInterrupted()) 42 { 43 if (selector.select(TIME_OUT)>0) 44 { 45 logger.warn("第【{}】輪監聽===============================================", 46 selectorNos.incrementAndGet()); 47 //獲取事件類型 48 Set<SelectionKey> selectionKeys = selector.selectedKeys(); 49 //selector監聽到的ready事件集 50 Iterator<SelectionKey> readyKeys = selectionKeys.iterator(); 51 //處理事件 52 while (readyKeys.hasNext()) 53 { 54 SelectionKey key = readyKeys.next(); 55 //移除channel事件 56 readyKeys.remove(); 57 SocketChannel socketChannel =null; 58 try { 59 60 //連接 61 if (key.isValid()&&key.isAcceptable()) { 62 socketChannel = ((ServerSocketChannel) key.channel()).accept(); 63 socketChannel.configureBlocking(false); 64 logger.info("Accept 收到了來自於【{}】的連接請求", socketChannel.getRemoteAddress()); 65 //將客戶端的可讀事件注冊到selector中監聽 66 socketChannel.register(key.selector(), SelectionKey.OP_READ); 67 } 68 //數據可讀 69 if (key.isValid()&&key.isReadable()) { 70 socketChannel = (SocketChannel)key.channel(); 71 logger.info("Readable 客戶端【{}】准備好了數據 ",socketChannel.getRemoteAddress()); 72 getRequestData(key); 73 } 74 if (key.isValid()&&key.isWritable()) 75 { 76 // if (RandomUtil.randomInt(0,10)>8) 77 // { 78 // doResponse(key); 79 // } 80 } 81 }catch (IOException ioException) 82 { 83 logger.error("服務端IO異常:\n",ioException.getCause()); 84 if (!Objects.isNull(socketChannel)) 85 { 86 socketChannel.close(); 87 key.cancel(); 88 } 89 } 90 } 91 } 92 } 93 //關閉channel 94 serverSocketChannel.close(); 95 selector.close(); 96 logger.info("進程退出"); 97 } 98 //處理連接請求 99 private static void getRequestData(SelectionKey selectionKey) throws IOException { 100 SocketChannel socketChannel = (SocketChannel)selectionKey.channel(); 101 //寫入數據到buffer 102 try { 103 if (socketChannel.isOpen()) 104 { 105 //將寫事件注冊到selector 106 // socketChannel.register(selectionKey.selector(), selectionKey.interestOps()|SelectionKey.OP_WRITE); 107 //准備buffer 108 ByteBuffer byteBuffer = ByteBuffer.allocate(2048); 109 StringBuilder content = new StringBuilder(); 110 int readBytes = 0; 111 while ((readBytes=socketChannel.read(byteBuffer))>0) { 112 //處理數據 113 content.append(new String(byteBuffer.array(), StandardCharsets.UTF_8)); 114 byteBuffer.clear(); 115 } 116 //判斷客戶端斷開連接 117 //當客戶端沒有斷開連接的時候readBytes=0這樣保持長連接 118 //當客戶端斷開連接的時候readBytes=-1 119 if (readBytes<0) 120 { 121 logger.debug("遠程客戶端【{}】斷開連接.....",socketChannel.getRemoteAddress()); 122 socketChannel.close(); 123 selectionKey.cancel(); 124 } 125 //處理數據 126 else { 127 logger.info("第【{}】次處理數據,收到的內容是: {}",handleDataNo.incrementAndGet(), 128 content.toString()); 129 } 130 131 } 132 else { 133 logger.warn("channel 已經關閉!"); 134 socketChannel.shutdownInput(); 135 socketChannel.shutdownOutput(); 136 socketChannel.close(); 137 selectionKey.cancel(); 138 } 139 }catch (Exception e) 140 { 141 logger.error("客戶端【{}】錯誤:",socketChannel,e.getCause()); 142 //關閉連接 143 socketChannel.shutdownInput(); 144 socketChannel.shutdownOutput(); 145 //將channel從selector中刪除 146 selectionKey.cancel(); 147 logger.info("socketChannel【{}】已經從selector取消注冊",socketChannel.getRemoteAddress()); 148 socketChannel.close(); 149 } 150 } 151 //返回響應數據 152 private static void doResponse(SelectionKey selectionKey) throws IOException { 153 SocketChannel socketChannel = (SocketChannel)selectionKey.channel(); 154 String resData=resDataNo.incrementAndGet()+"=========>"+ RandomUtil.randomStringUpper(10); 155 logger.debug("響應數據[{}]到【{}】",resData,socketChannel.getRemoteAddress()); 156 socketChannel.write(ByteBuffer.wrap(resData.getBytes())); 157 } 158 }
先后啟動服務端和客戶端,運行結果:
服務端運行日志:
11:01:16.817 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 服務在[/0:0:0:0:0:0:0:0:17899]啟動成功,正在監聽事件。。。。。 11:01:19.840 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【1】輪監聽=============================================== 11:01:19.841 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63958】的連接請求 11:01:19.841 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【2】輪監聽=============================================== 11:01:19.841 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63959】的連接請求 11:01:19.842 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【3】輪監聽=============================================== 11:01:19.843 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63960】的連接請求 11:01:19.843 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【4】輪監聽=============================================== 11:01:19.843 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63961】的連接請求 11:01:19.847 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【5】輪監聽=============================================== 11:01:19.847 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63962】的連接請求 11:01:19.848 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【6】輪監聽=============================================== 11:01:19.848 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63963】的連接請求 11:01:19.850 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【7】輪監聽=============================================== 11:01:19.850 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63964】的連接請求 11:01:19.851 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【8】輪監聽=============================================== 11:01:19.851 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63965】的連接請求 11:01:19.853 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【9】輪監聽=============================================== 11:01:19.853 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63966】的連接請求 11:01:19.853 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【10】輪監聽=============================================== 11:01:19.854 [main] INFO com.vincent.fat.core.nio.server.NioServer - Accept 收到了來自於【/127.0.0.1:63967】的連接請求 11:01:20.091 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【11】輪監聽=============================================== 11:01:20.091 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63962】准備好了數據 11:01:20.092 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【1】次處理數據,收到的內容是: 63962==========>西南科技大學 11:01:20.092 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【12】輪監聽=============================================== 11:01:20.092 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63964】准備好了數據 11:01:20.092 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【2】次處理數據,收到的內容是: 63964==========>西北技術大學 11:01:20.094 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【13】輪監聽=============================================== 11:01:20.095 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63961】准備好了數據 11:01:20.095 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【3】次處理數據,收到的內容是: 63961==========>西科技大學 11:01:20.095 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【14】輪監聽=============================================== 11:01:20.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63958】准備好了數據 11:01:20.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【4】次處理數據,收到的內容是: 63958==========>東大學 11:01:20.096 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【15】輪監聽=============================================== 11:01:20.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63959】准備好了數據 11:01:20.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【5】次處理數據,收到的內容是: 63959==========>西北科技大學 11:01:20.100 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【16】輪監聽=============================================== 11:01:20.100 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63960】准備好了數據 11:01:20.101 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【6】次處理數據,收到的內容是: 63960==========>西南大學 11:01:20.102 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【17】輪監聽=============================================== 11:01:20.102 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63965】准備好了數據 11:01:20.102 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【7】次處理數據,收到的內容是: 63965==========>西南科技大學 11:01:20.102 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【18】輪監聽=============================================== 11:01:20.102 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63967】准備好了數據 11:01:20.102 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【8】次處理數據,收到的內容是: 63967==========>東科技大學 11:01:20.103 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【19】輪監聽=============================================== 11:01:20.103 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63963】准備好了數據 11:01:20.103 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【9】次處理數據,收到的內容是: 63963==========>西南體育大學 11:01:20.105 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【20】輪監聽=============================================== 11:01:20.105 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63966】准備好了數據 11:01:20.105 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【10】次處理數據,收到的內容是: 63966==========>北理工大學 11:01:23.093 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【21】輪監聽=============================================== 11:01:23.093 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63962】准備好了數據 11:01:23.093 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【11】次處理數據,收到的內容是: 63962==========>中國藝術大學 11:01:23.094 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【22】輪監聽=============================================== 11:01:23.094 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63964】准備好了數據 11:01:23.095 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【12】次處理數據,收到的內容是: 63964==========>北藝術大學 11:01:23.095 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【23】輪監聽=============================================== 11:01:23.095 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63961】准備好了數據 11:01:23.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【13】次處理數據,收到的內容是: 63961==========>北體育大學 11:01:23.096 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【24】輪監聽=============================================== 11:01:23.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63958】准備好了數據 11:01:23.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【14】次處理數據,收到的內容是: 63958==========>南農業大學 11:01:23.098 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【25】輪監聽=============================================== 11:01:23.098 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63959】准備好了數據 11:01:23.098 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【15】次處理數據,收到的內容是: 63959==========>西藝術大學 11:01:23.103 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【26】輪監聽=============================================== 11:01:23.103 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63960】准備好了數據 11:01:23.103 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【16】次處理數據,收到的內容是: 63960==========>南科技大學 11:01:23.103 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【27】輪監聽=============================================== 11:01:23.103 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63967】准備好了數據 11:01:23.103 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【17】次處理數據,收到的內容是: 63967==========>南農業大學 11:01:23.104 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【28】輪監聽=============================================== 11:01:23.104 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63965】准備好了數據 11:01:23.104 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【18】次處理數據,收到的內容是: 63965==========>西北技術大學 11:01:23.105 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【29】輪監聽=============================================== 11:01:23.105 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63963】准備好了數據 11:01:23.105 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【19】次處理數據,收到的內容是: 63963==========>西科技大學 11:01:23.106 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【30】輪監聽=============================================== 11:01:23.106 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63966】准備好了數據 11:01:23.106 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【20】次處理數據,收到的內容是: 63966==========>西經貿大學 11:01:26.094 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【31】輪監聽=============================================== 11:01:26.095 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63962】准備好了數據 11:01:26.095 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【21】次處理數據,收到的內容是: 63962==========>東南科技大學 11:01:26.096 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【32】輪監聽=============================================== 11:01:26.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63964】准備好了數據 11:01:26.097 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【22】次處理數據,收到的內容是: 63964==========>西南藝術大學 11:01:26.097 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【33】輪監聽=============================================== 11:01:26.097 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63961】准備好了數據 11:01:26.097 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【23】次處理數據,收到的內容是: 63961==========>東南體育大學 11:01:26.098 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【34】輪監聽=============================================== 11:01:26.098 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63958】准備好了數據 11:01:26.098 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【24】次處理數據,收到的內容是: 63958==========>南藝術大學 11:01:26.099 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【35】輪監聽=============================================== 11:01:26.100 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63959】准備好了數據 11:01:26.100 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【25】次處理數據,收到的內容是: 63959==========>中國技術大學 11:01:26.104 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【36】輪監聽=============================================== 11:01:26.104 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63967】准備好了數據 11:01:26.104 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【26】次處理數據,收到的內容是: 63967==========>北科技大學 11:01:26.105 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【37】輪監聽=============================================== 11:01:26.105 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63960】准備好了數據 11:01:26.105 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【27】次處理數據,收到的內容是: 63960==========>東北理工大學 11:01:26.106 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【38】輪監聽=============================================== 11:01:26.106 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63965】准備好了數據 11:01:26.106 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【28】次處理數據,收到的內容是: 63965==========>西科技大學 11:01:26.107 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【39】輪監聽=============================================== 11:01:26.107 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63963】准備好了數據 11:01:26.107 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【29】次處理數據,收到的內容是: 63963==========>東北體育大學 11:01:26.110 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【40】輪監聽=============================================== 11:01:26.110 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63966】准備好了數據 11:01:26.110 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【30】次處理數據,收到的內容是: 63966==========>中國大學 11:01:29.096 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【41】輪監聽=============================================== 11:01:29.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63962】准備好了數據 11:01:29.096 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【31】次處理數據,收到的內容是: 63962==========>東北農業大學 11:01:29.098 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【42】輪監聽=============================================== 11:01:29.098 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63964】准備好了數據 11:01:29.099 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【32】次處理數據,收到的內容是: 63964==========>西北農業大學 11:01:29.099 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【43】輪監聽=============================================== 11:01:29.099 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63958】准備好了數據 11:01:29.100 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【33】次處理數據,收到的內容是: 63958==========>南體育大學 11:01:29.100 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【44】輪監聽=============================================== 11:01:29.100 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63961】准備好了數據 11:01:29.100 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【34】次處理數據,收到的內容是: 63961==========>北大學 11:01:29.101 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【45】輪監聽=============================================== 11:01:29.102 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63959】准備好了數據 11:01:29.102 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【35】次處理數據,收到的內容是: 63959==========>東農業大學 11:01:29.106 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【46】輪監聽=============================================== 11:01:29.106 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63960】准備好了數據 11:01:29.107 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【36】次處理數據,收到的內容是: 63960==========>南大學 11:01:29.107 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【47】輪監聽=============================================== 11:01:29.107 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63967】准備好了數據 11:01:29.107 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【37】次處理數據,收到的內容是: 63967==========>中國大學 11:01:29.108 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【48】輪監聽=============================================== 11:01:29.108 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63965】准備好了數據 11:01:29.108 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【38】次處理數據,收到的內容是: 63965==========>西科技大學 11:01:29.109 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【49】輪監聽=============================================== 11:01:29.110 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63963】准備好了數據 11:01:29.110 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【39】次處理數據,收到的內容是: 63963==========>南科技大學 11:01:29.112 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【50】輪監聽=============================================== 11:01:29.112 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63966】准備好了數據 11:01:29.112 [main] INFO com.vincent.fat.core.nio.server.NioServer - 第【40】次處理數據,收到的內容是: 63966==========>西北科技大學 11:01:29.825 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【51】輪監聽=============================================== 11:01:29.825 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63965】准備好了數據 11:01:29.825 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63965】斷開連接..... 11:01:29.826 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【52】輪監聽=============================================== 11:01:29.826 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63962】准備好了數據 11:01:29.826 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63962】斷開連接..... 11:01:29.827 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【53】輪監聽=============================================== 11:01:29.827 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63961】准備好了數據 11:01:29.827 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63961】斷開連接..... 11:01:29.828 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【54】輪監聽=============================================== 11:01:29.828 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63958】准備好了數據 11:01:29.828 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63958】斷開連接..... 11:01:29.831 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【55】輪監聽=============================================== 11:01:29.831 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63966】准備好了數據 11:01:29.831 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63966】斷開連接..... 11:01:29.831 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【56】輪監聽=============================================== 11:01:29.832 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63959】准備好了數據 11:01:29.832 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63959】斷開連接..... 11:01:29.833 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【57】輪監聽=============================================== 11:01:29.833 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63963】准備好了數據 11:01:29.833 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63963】斷開連接..... 11:01:29.844 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【58】輪監聽=============================================== 11:01:29.844 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63960】准備好了數據 11:01:29.844 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63960】斷開連接..... 11:01:29.844 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【59】輪監聽=============================================== 11:01:29.845 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63964】准備好了數據 11:01:29.845 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63964】斷開連接..... 11:01:29.846 [main] WARN com.vincent.fat.core.nio.server.NioServer - 第【60】輪監聽=============================================== 11:01:29.846 [main] INFO com.vincent.fat.core.nio.server.NioServer - Readable 客戶端【/127.0.0.1:63967】准備好了數據 11:01:29.846 [main] DEBUG com.vincent.fat.core.nio.server.NioServer - 遠程客戶端【/127.0.0.1:63967】斷開連接.....
客戶端日志:
"C:\Program Files\Java\jdk1.8.0_221\bin\java.exe" -agentlib:jdwp=transport=dt_socket,address=127.0.0.1:63949,suspend=y,server=n -javaagent:C:\Users\wb-swz696586\AppData\Local\JetBrains\IntelliJIdea2020.1\captureAgent\debugger-agent.jar -Dfile.encoding=UTF-8 -classpath "D:\softs\IntelliJ IDEA 2019.3.4\lib\idea_rt.jar" com.intellij.rt.execution.CommandLineWrapper C:\Users\wb-swz696586\AppData\Local\Temp\idea_classpath1497081722 com.vincent.fat.core.nio.client.NioClient Connected to the target VM, address: '127.0.0.1:63949', transport: 'socket' 11:01:19.846 [pool-1-thread-7] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63958]完成連接 11:01:19.851 [pool-1-thread-2] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63965]完成連接 11:01:19.849 [pool-1-thread-4] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63959]完成連接 11:01:19.847 [pool-1-thread-6] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63962]完成連接 11:01:19.848 [pool-1-thread-5] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63960]完成連接 11:01:19.854 [pool-1-thread-3] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63966]完成連接 11:01:19.848 [pool-1-thread-10] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63961]完成連接 11:01:19.850 [pool-1-thread-1] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63964]完成連接 11:01:19.848 [pool-1-thread-8] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63963]完成連接 11:01:19.853 [pool-1-thread-9] DEBUG com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - [/127.0.0.1:63967]完成連接 11:01:20.092 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63962]的第【1】條數據發送完成 11:01:20.092 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63964]的第【2】條數據發送完成 11:01:20.095 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63961]的第【3】條數據發送完成 11:01:20.095 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63958]的第【4】條數據發送完成 11:01:20.097 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63959]的第【5】條數據發送完成 11:01:20.100 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63960]的第【6】條數據發送完成 11:01:20.101 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63967]的第【7】條數據發送完成 11:01:20.103 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63963]的第【9】條數據發送完成 11:01:20.102 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63965]的第【8】條數據發送完成 11:01:20.105 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63966]的第【10】條數據發送完成 11:01:23.092 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.093 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63962]的第【11】條數據發送完成 11:01:23.094 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.094 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63964]的第【12】條數據發送完成 11:01:23.095 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.095 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63961]的第【13】條數據發送完成 11:01:23.096 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.096 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63958]的第【14】條數據發送完成 11:01:23.097 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.098 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63959]的第【15】條數據發送完成 11:01:23.101 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.102 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.103 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63960]的第【16】條數據發送完成 11:01:23.103 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63967]的第【17】條數據發送完成 11:01:23.104 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.104 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.104 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63963]的第【18】條數據發送完成 11:01:23.104 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63965]的第【19】條數據發送完成 11:01:23.106 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:23.106 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63966]的第【20】條數據發送完成 11:01:26.094 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.094 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63962]的第【21】條數據發送完成 11:01:26.096 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.096 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63964]的第【22】條數據發送完成 11:01:26.097 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.097 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.097 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63961]的第【23】條數據發送完成 11:01:26.097 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63958]的第【24】條數據發送完成 11:01:26.099 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.099 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63959]的第【25】條數據發送完成 11:01:26.104 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.104 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.104 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63960]的第【26】條數據發送完成 11:01:26.104 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63967]的第【27】條數據發送完成 11:01:26.105 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.105 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.106 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63965]的第【28】條數據發送完成 11:01:26.107 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63963]的第【29】條數據發送完成 11:01:26.107 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:26.110 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63966]的第【30】條數據發送完成 11:01:29.095 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.096 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63962]的第【31】條數據發送完成 11:01:29.097 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.098 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.098 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.098 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63964]的第【32】條數據發送完成 11:01:29.099 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63958]的第【33】條數據發送完成 11:01:29.100 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63961]的第【34】條數據發送完成 11:01:29.101 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.101 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63959]的第【35】條數據發送完成 11:01:29.105 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.105 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.106 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63967]的第【36】條數據發送完成 11:01:29.106 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63960]的第【37】條數據發送完成 11:01:29.107 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.108 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63965]的第【38】條數據發送完成 11:01:29.108 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.109 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63963]的第【39】條數據發送完成 11:01:29.111 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 收到的內容是: <> 11:01:29.112 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 客戶端[/127.0.0.1:63966]的第【40】條數據發送完成 11:01:29.823 [pool-1-thread-2] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63965的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.824 [pool-1-thread-6] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63962的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.826 [pool-1-thread-6] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63962】的輸出通道關閉! 11:01:29.826 [pool-1-thread-10] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63961的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.827 [pool-1-thread-10] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63961】的輸出通道關閉! 11:01:29.827 [pool-1-thread-7] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63958的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.828 [pool-1-thread-7] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63958】的輸出通道關閉! 11:01:29.829 [pool-1-thread-3] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63966的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.831 [pool-1-thread-3] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63966】的輸出通道關閉! 11:01:29.823 [pool-1-thread-4] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63959的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.832 [pool-1-thread-4] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63959】的輸出通道關閉! 11:01:29.832 [pool-1-thread-8] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63963的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.833 [pool-1-thread-8] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63963】的輸出通道關閉! 11:01:29.833 [pool-1-thread-5] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63960的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.835 [pool-1-thread-5] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63960】的輸出通道關閉! 11:01:29.825 [pool-1-thread-2] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63965】的輸出通道關閉! 11:01:29.837 [pool-1-thread-1] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63964的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.838 [pool-1-thread-1] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63964】的輸出通道關閉! 11:01:29.845 [pool-1-thread-9] ERROR com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 端口為63967的客戶端報錯 java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at java.lang.Thread.sleep(Thread.java:340) at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.doRequest(RequestRemoteServerWithTcp.java:70) at com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp.run(RequestRemoteServerWithTcp.java:49) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:266) at java.util.concurrent.FutureTask.run(FutureTask.java) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:01:29.847 [pool-1-thread-9] INFO com.vincent.fat.core.nio.client.RequestRemoteServerWithTcp - 【63967】的輸出通道關閉! Disconnected from the target VM, address: '127.0.0.1:63949', transport: 'socket' Process finished with exit code 0
為了保持長連接,在客戶端發送完一次數據以后socketChannel沒有關閉,服務端接收完成一次數據以后socketChannel也沒有關閉,這樣再下次發送數據的時候可以直接發送。但是當客戶端線程被中斷以后,客戶端關閉了sockeChannel,此時服務端沒有相應的API判斷客戶端是否關閉了socket,導致selector在監聽事件的時候會無限堅挺到readable()事件,導致CPU等資源大量浪費,系統崩潰。可以通過如下代碼來判斷客戶端socket是否關閉:
int readBytes = 0; while ((readBytes=socketChannel.read(byteBuffer))>0) { //處理數據 content.append(new String(byteBuffer.array(), StandardCharsets.UTF_8)); byteBuffer.clear(); } //判斷客戶端斷開連接 //當客戶端沒有斷開連接的時候readBytes=0這樣保持長連接 //當客戶端斷開連接的時候readBytes=-1 if (readBytes<0) { logger.debug("遠程客戶端【{}】斷開連接.....",socketChannel.getRemoteAddress()); socketChannel.close(); selectionKey.cancel(); } //處理數據 else { logger.info("第【{}】次處理數據,收到的內容是: {}",handleDataNo.incrementAndGet(), content.toString()); }
socketChannel.read()此函數返回客戶端讀取到的字節數,如果大於0 代表有數據讀取到,如果=-1代表客戶端關閉了連接,此時可以調用 selectionKey.cancel();取消此channel對相應selector的注冊。從而避免無限循環的BUG。