在開發 Java 客戶端/伺服器系統時,網路非同步處理是確保系統穩定性的關鍵。當伺服端發生故障或重啟時,客戶端應能自動偵測並重新連線,而不阻塞其他任務。本文介紹一種基於 javax.swing.Timer 的非同步通訊架構,封裝於 NetComm 類別中,讓應用層無感知定時器的存在,專注於業務邏輯。
NetComm 實作 ActionListener,內含一個週期 3 秒的 Timer 與狀態機 net_state(0=斷線/待連,1=已連)。主要方法:
NetComm_Init():嘗試建立 Socket 連線,成功啟動定時器,失敗重設狀態。NetComm_Data():讀寫資料流,遇到 IOException 呼叫 NetComm_Close() 關閉連線並歸零狀態。actionPerformed():定時器觸發點,依狀態決定執行初始化或資料收發。public class NetComm implements ActionListener {
private javax.swing.Timer timer = new javax.swing.Timer(3000, this);
private Socket sock;
private InetAddress serverAddr;
private int serverPort;
public static int net_state = 0;
public NetComm(InetAddress addr, int port) {
this.serverAddr = addr;
this.serverPort = port;
}
public void NetComm_Init() {
net_state = 1;
try {
sock = new Socket(serverAddr, serverPort);
} catch (IOException e) {
net_state = 0;
}
timer.start();
}
public void NetComm_Data() {
try (OutputStream os = sock.getOutputStream();
BufferedWriter out = new BufferedWriter(new OutputStreamWriter(os));
BufferedReader in = new BufferedReader(new InputStreamReader(sock.getInputStream()))) {
out.write("Java Client");
out.flush();
String line;
while ((line = in.readLine()) != null) {
System.out.println(line); // 處理接收資料
}
} catch (IOException e) {
NetComm_Close();
net_state = 0;
}
timer.start();
}
public void NetComm_Close() {
if (sock != null) {
try { sock.close(); } catch (IOException ignored) {}
}
}
@Override
public void actionPerformed(ActionEvent e) {
if (net_state == 0) NetComm_Init();
else NetComm_Data();
}
}
可引入回呼介面 EventNotifier,於連線建立、斷開、重連成功時通知上層應用,實現解耦。伺服端同樣可套用此模式,只需調整監聽與接受連線的邏輯。
此模式將「連線管理」與「業務處理」分離,利用定時器輪詢實現非同步自動重連,適合需長時間運行、對網路波動具彈性的 Java 網路應用。