Каков наилучший способ установить тайм-аут для закрытия NIO SocketChannel, если в течение определенного периода после установления соединения данные не получены?
Тайм-аут чтения для NIO SocketChannel?
Ответы:
Либо:
Вы используете
Selector
, и в этом случае у вас есть время ожидания, с которым вы можете играть, и если оно срабатывает (select(timeout)
возвращает ноль), вы закрываете все зарегистрированные каналы илиВы используете режим блокировки, и в этом случае вы можете подумать, что должны иметь возможность вызывать
Socket.setSoTimeout()
в базовом сокете (SocketChannel.socket()
) и перехватыватьSocketTimeoutException
, который выдается по истечении времени ожидания во времяread()
, но вы не можете, потому что это не поддерживается для сокетов, происходящих как каналы, илиВы используете неблокирующий режим без
Selector
, и в этом случае вам нужно перейти на случай (1).
Таким образом, вам нужно либо использовать случай (1), либо java.net.Socket
напрямую.
Я искал ту же рекомендацию и не мог легко ее найти - делюсь ею здесь.
Для netty есть хороший обработчик: ReadTimeoutHandler.
Можно использовать так
channel.pipeline().addLast(new ReadTimeoutHandler(readTimeout));
он сбросит io.netty.handler.timeout.ReadTimeoutException, если не сможет увидеть какие-либо данные, выполняющие определенный тайм-аут чтения.