Почему мой метод декодирования ByteToMessageDecoder никогда не вызывается? - PullRequest
0 голосов
/ 17 октября 2018

Я пытаюсь справиться с Нетти.Я использую HTTP для своего примера здесь (я знаю, что в библиотеке есть HTTP (de / en) -кодеры, но смысл этого упражнения для меня - понять, как работает конвейер.

Iиметь простой конвейер, построенный следующим образом:

b.handler(new ChannelInitializer<SocketChannel>() {
  @Override
  protected void initChannel(SocketChannel socketChannel){
    socketChannel.pipeline().addLast(new Announcer());
    socketChannel.pipeline().addLast(new Receiver());
    socketChannel.pipeline().addLast(new Source());
  }
});

Извещатель MessageToByteEncoder<String> с методом encode:

@Override
protected void encode(ChannelHandlerContext ctx, String msg, ByteBuf out) {
  byte[] bytes = msg.getBytes(CharsetUtil.US_ASCII);
  out.writeBytes(bytes);
}

Источник ChannelOutboundHandlerAdapter с методом read:

@Override
public void read(ChannelHanderContext ctx) {
  String path = "/";
  String host = "xkcd.com"
  String content = "GET " + path + " HTTP/1.1\n" +
    "Host: " + host + "\n" +
    "\n";
  ctx.writeAndFlush(content);
}

Получатель - ByteToMessageDecoder с методом decode:

@Override
protected void decode(ChannelHandlerContext ctx, ByteBuf in, List<Object> out) {
    String e = in.toString(CharsetUtil.UTF_8);
    System.err.println(e);
    out.add(e);
}

Я проверил, что вывод Source является допустимым HTTP-запросом и получает ответfrom xkcd.com:80

Я вижу методы Source и затем Announcer, вызванные для генерации запроса, но Я никогда не вижу метод декодирования Receiver, называемый .

Почему?

1 Ответ

0 голосов
/ 17 октября 2018

В реализации декодера

Вы обнаружите, что для входящих данных метод / событие channelRead переопределяется.Этот метод вызывается для каждого сообщения, которое читается с входящего канала.Затем он вызовет метод decode() предоставленного декодера и перенаправит декодированные байты на следующий ChannelInboundHandler в конвейере.

В вашем случае вы переопределили метод readChannelOutboundHandlerAdapter и вы не вызываете ctx.read() внутри этого метода.Это означает, что он предотвратит вызов метода channelRead любого ChannelInboundHandler и, следовательно, метода decode любого декодера.В вашем случае Source класс запрещает чтение с канала.Кроме того, целью переопределения метода чтения ChannelOutboundHandlerAdapter не должно быть запись чего-либо в канал.

Ниже приводится определение метода чтения.

read(ChannelHandlerContext) Вызывается по запросу для чтения дополнительных данных с Канала

Вы можете прочитать Нетти в действии Книга для лучшего понимания нетти.

...