2

Netty 4 发出警告“丢弃 1 条到达管道末端的入站消息。请检查您的管道配置”。这是什么意思?应该如何处理?(以前在这里复制,直到根据接受的答案解决,但我宁愿对它的含义和管道如何工作有一般性的解释)

为了最大化网络反馈,客户端管道设置如下:

pipeline.addLast("logger", new LoggingHandler(LogLevel.TRACE))
pipeline.addLast("HttpRequestEncoder", new HttpClientCodec)
pipeline.addLast("handler", new myHandler)

我通过 Netty 在客户端登录,同时它发送了两条 http 消息并被服务器端成功接收和确认:

12 [main] DEBUG io.netty.util.internal.InternalLoggerFactory  - Using Log4J as the default logging framework
164 [nioEventLoopGroup-1-2] DEBUG io.netty.channel.nio.SelectorUtil  - Using select timeout of 500
164 [nioEventLoopGroup-1-2] DEBUG io.netty.channel.nio.SelectorUtil  - Epoll-bug workaround enabled = false
229 [nioEventLoopGroup-1-2] WARN io.netty.channel.DefaultChannelPipeline  - Discarded 1 inbound message(s) that reached at the end of the pipeline. Please check your pipeline configuration.
230 [nioEventLoopGroup-1-2] WARN io.netty.channel.DefaultChannelPipeline  - Discarded 1 inbound message(s) that reached at the end of the pipeline. Please check your pipeline configuration.

而日志记录是这样设置的:

BasicConfigurator.configure       
InternalLoggerFactory.setDefaultFactory(new Log4JLoggerFactory)
4

4 回答 4

5

在 Netty 4 中,用于服务器或客户端的 HTTP 解码器总是为每个 HTTP 消息生成多个消息对象:

1       * HttpRequest / HttpResponse
0 - n   * HttpContent
1       * LastHttpContent

换句话说:

  • 服务器接收 1 个 HttpRequest、0-n 个 HttpContent(s) 和 1 个 HttpLastContent
  • 客户端接收 1 个 HttpResponse、0-n 个 HttpContent(s) 和 1 个 HttpLastContent。

因此,如果您的处理程序仅使用 HttpRequest/HttpResponse,则其他消息将到达管道的末尾。您需要使用它们,这是您的管道“配置错误”的地方。

OTOH,您可以将 HttpObjectAggregator 添加到管道中,以便生成 FullHttpRequest/FullHttpResponse 消息:

pipeline.addLast( "http-aggregator", new HttpObjectAggregator( MAX_SIZE ) );

但这意味着在调用您的处理程序之前加载整个请求或响应,包括正文实体。也许你不想那样,YMMV。

于 2013-03-22T16:36:59.400 回答
4

Netty 4 自动在您创建的管道上添加最后一个处理程序,如果事件到达最后一个处理程序,它将通过消息。您的最后一个入站处理程序不应触发上下文事件。

删除这个:ctx.fireChannelRead(msg);

于 2014-11-24T20:31:26.530 回答
2

@eskatos 是对的,管道的 handler 处理基于类型匹配,例如,SimpleChannelInboundHandler<HttpContent>只会处理 HttpContent,如果你还没有处理 HttpReponse(添加SimpleChannelInboundHandler<HttpReponse>到你的管道中),Netty 会警告:Content-Length:<length>到达尾部管道。请检查您的管道配置。

因此,解决方案是将相应的添加ChannelInboundHandler/ChannelOutboundHandler到您的管道中。

但是您需要首先知道输入的 Handler 缺少什么:找到 DefaultChannelPipeline 的 channelRead 方法并对其进行调试以获取 msg.content().toString() ,其中包括缺少的消息。

还有一件事,@Norman Maurer提到启用调试日志记录不起作用,因为 channelRead 方法不会记录 msg 内容中的内容。

下面是 DefaultChannelPipeline 的 channelRead 方法(Netty 4.1):

    @Override
    public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
        try {
            logger.debug(
                    "Discarded inbound message {} that reached at the tail of the pipeline. " +
                            "Please check your pipeline configuration.", msg);
        } finally {
            ReferenceCountUtil.release(msg);
        }
    }
于 2015-08-26T06:47:52.187 回答
1

这意味着一条消息到达了管道的末端,并且没有“入站处理程序”能够处理它。这在大多数情况下会在 ChannelPipeline 中显示“配置”错误。

于 2013-03-06T19:41:05.380 回答