號這被許多人誤解了,可惜有很多誤傳那裏。
首先,「無限」是一種半有效值。有兩個特殊的配置序列化器可將「無限」轉換爲TimeSpan.MaxValue
或int.MaxValue
(因此它們不是真正的「無限」),但並非WCF中的所有內容似乎都能識別這一點。所以最好是用時間值明確指定你的超時時間。
其次,您的服務中不需要「keepalive」方法,因爲WCF提供了所謂的「可靠會話」。如果添加<reliableSession enabled="true" />
,則WCF將通過「基礎結構消息」提供它自己的保持活動機制。
通過擁有自己的「keepalive」機制,您的服務負載實際上翻了一番,而且實際上可以創建比解決問題更多的問題。
第三,使用可靠的會話時,可以使用inactivityTimeout
設置reliableSession
。這有兩件事。首先,它控制發送基礎設施(Keepalive)消息的頻率。它們以超時值的一半發送,所以如果將它設置爲18分鐘,那麼它們將每9分鐘發送一次。其次,如果在不活動超時時間內沒有收到基礎設施或操作消息(即,屬於數據合同的消息),則連接會中止,因爲可能存在問題(一方崩潰,存在網絡問題等)。 )。
receiveTimeout
是連接中止前未接收到操作消息的最大時間量(默認值爲10分鐘)。將此值設置爲較大的值(Int32.MaxValue
位於24天附近的某個位置)可以保持連接不變,將inactivityTimeout設置爲較小的值(再次默認爲10分鐘)(時間小於最大值的2倍在網絡路由器將連接從不活動狀態中斷開之前)保持連接處於活動狀態。
WCF爲您處理所有這些事情。然後,您可以簡單地訂閱連接中止消息,以瞭解由於真正原因(應用程序崩潰,網絡超時,客戶端斷電等)何時斷開連接,並允許您重新創建連接。
此外,如果您不需要有序消息,請設置ordered="false"
,因爲這可以大大降低可靠會話的開銷。默認值是true。
注意:您可能不會收到連接中止事件,直到inactivityTimeout過期(或者您嘗試使用連接)。注意這一點,並相應地設置你的超時時間。
互聯網上的大多數建議是將receiveTimeout和inactivityTimeout都設置爲無限。這有兩個問題,第一個基礎設施消息沒有及時發送,所以路由器會斷開連接......迫使你做自己的keepalive。其次,大量非活動超時意味着它不會識別何時合法連接斷開,並且您必須依靠該中止來確定何時發生故障。這完全沒有必要,實際上甚至可能使您的服務更加不可靠。
如果您打算保持連接處於打開狀態,您必須定期發送ping數據包,否則有狀態路由器可能會由於不活動而丟棄連接。 – 2014-11-04 11:56:13
好的,我怎麼知道這個ping必須被髮送的頻率? – Banshee 2014-11-04 12:09:04
連接由於瞬時錯誤而下降時會發生什麼?你無法阻止這一點。 – usr 2014-11-04 13:02:41