У меня есть сервер, который получает запросы на установление соединения от клиентов. Этот сервер использует асинхронное Socket.BeginReceive
и Socket.EndReceive
метод. Код довольно подобен коду, найденному здесь.
В моем случае, после вызова Socket.BeginReceive
Мне нужен тайм-аут, таким образом, что, если клиент держится за соединение, но не передает данных вообще для фиксированного количества времени, я должен завершить соединение.
Просто вызовите метод сокета Close ()
. После этого метод обратного вызова будет выполняться довольно быстро, вы получите исключение ObjectDisposedException
, когда вызовете метод EndReceive ()
. Будьте готовы перехватить это исключение.
Вероятно, вы не хотите блокировать поток, который вызвал BeginReceive
, вам понадобится System.Threading.Timer
или System.Timers.Timer
для определения тайм-аута. Его обратный вызов должен вызывать Close ()
. Остерегайтесь неизбежного состояния гонки, которое это вызывает, обратный вызов таймера будет запущен, если ответ был получен за микросекунду до истечения таймера. Вы закроете сокет, даже если получите хороший ответ.
Согласно статье MSDN на Socket.BeginReceive , в ней указано
Чтобы отменить ожидающий BeginReceive, вызовите метод Close.
Вы можете получать некоторые начальные данные асинхронно, а затем выполнять синхронный прием для остальных данных и полагаться на ReceiveTimeout для отключения клиента. Вы можете использовать Socket.Close для принудительного отключения клиента.
Но если вы хотите использовать только асинхронный прием, тогда вы можете использовать таймеры и сбросить их на EndReceive. По истечении этого срока вы можете принудительно отключить клиента.
Но я думаю, что первый подход лучше.