TCP 閘道器

入站 TCP 閘道器 TcpInboundGateway 和出站 TCP 閘道器 TcpOutboundGateway 分別使用伺服器和客戶端連線工廠。每個連線一次可以處理一個請求或響應。

入站閘道器在用傳入的有效載荷構建訊息並將其傳送到 requestChannel 後,等待響應並將其有效載荷從響應訊息寫入連線來發送。

對於入站閘道器,您必須保留或填充 ip_connectionId 標頭,因為它用於將訊息與連線關聯。源自閘道器的訊息會自動設定該標頭。如果回覆是作為新訊息構建的,則需要設定該標頭。標頭值可以從傳入訊息中捕獲。

與入站介面卡一樣,入站閘道器通常使用 type="server" 連線工廠,它監聽傳入的連線請求。在某些情況下,您可能希望反向建立連線,使得入站閘道器連線到外部伺服器,然後在該連線上等待並回復入站訊息。

透過在入站閘道器上使用 client-mode="true" 來支援這種拓撲。在這種情況下,連線工廠必須是 client 型別,並且必須將 single-use 設定為 false

兩個附加屬性支援此機制。retry-interval 指定(以毫秒為單位)框架在連線失敗後嘗試重新連線的頻率。scheduler 提供一個 TaskScheduler 來排程連線嘗試並測試連線是否仍然活躍。

如果閘道器已啟動,您可以透過傳送 <control-bus/> 命令 @adapter_id.retryConnection() 來強制閘道器建立連線,並透過 @adapter_id.isClientModeConnected() 來檢查當前狀態。

出站閘道器在透過連線傳送訊息後,等待響應,構建響應訊息,並將其放入回覆通道。連線上的通訊是單執行緒的。一次只能處理一條訊息。如果另一個執行緒嘗試在當前響應被接收之前傳送訊息,它將阻塞直到任何先前的請求完成(或超時)。但是,如果客戶端連線工廠配置為單次使用的連線,則每個新請求都會獲得自己的連線並立即處理。以下示例配置了一個入站 TCP 閘道器。

<int-ip:tcp-inbound-gateway id="inGateway"
    request-channel="tcpChannel"
    reply-channel="replyChannel"
    connection-factory="cfServer"
    reply-timeout="10000"/>

如果使用配置了預設序列化器或反序列化器的連線工廠,訊息將是 \r\n 分隔的資料,閘道器可以由簡單的客戶端(如 telnet)使用。

以下示例顯示了一個出站 TCP 閘道器。

<int-ip:tcp-outbound-gateway id="outGateway"
    request-channel="tcpChannel"
    reply-channel="replyChannel"
    connection-factory="cfClient"
    request-timeout="10000"
    remote-timeout="10000"/> <!-- or e.g. remote-timeout-expression="headers['timeout']" -->

client-mode 目前不適用於出站閘道器。

從版本 5.2 開始,出站閘道器可以透過屬性 closeStreamAfterSend 進行配置。如果連線工廠配置為 single-use(每個請求/回覆使用一個新的連線),閘道器將關閉輸出流;這會向伺服器傳送 EOF 訊號。如果伺服器使用 EOF 而不是流中的某個分隔符來確定訊息的結束,但為了接收回復而保持連線開啟,這會很有用。

通常,呼叫執行緒將在閘道器中阻塞,等待回覆(或超時)。從版本 5.3 開始,您可以將閘道器上的 async 屬性設定為 true,傳送執行緒將被釋放以執行其他工作。回覆(或錯誤)將在接收執行緒上傳送。這僅適用於使用 TcpNetClientConnectionFactory 的情況,在使用 NIO 時會忽略它,因為存在一個競態條件,即在收到回覆之後發生的套接字錯誤可能會在回覆之前傳遞給閘道器。

當使用共享連線 (singleUse=false) 時,在一個請求正在處理時發出新請求,將阻塞直到收到當前回覆。如果您希望支援在長連線池上進行併發請求,請考慮使用 CachingClientConnectionFactory

從版本 5.4 開始,入站可以配置 unsolicitedMessageChannel。未經請求的入站訊息將傳送到此通道,以及延遲迴復(當客戶端超時時)。為了在伺服器端支援這一點,您現在可以向連線工廠註冊多個 TcpSender。閘道器和通道介面卡會自動註冊。從伺服器傳送未經請求的訊息時,您必須將適當的 IpHeaders.CONNECTION_ID 新增到傳送的訊息中。

© . This site is unofficial and not affiliated with VMware.