2015-03-02 4 views
3

Я использую netty 4.0.25Final для написания netty HTTP-сервера. Мне нужно добавить различные обработчики в конвейер в зависимости от некоторых параметров в запросе HTTP GET.динамически меняющийся нетто-конвейер

pipeline.addLast(new HttpRequestDecoder(4096, 8192, 8192, false), 
       new HttpResponseEncoder(), 
       new HttpObjectAggregator(1048576), 
       decisionHandler 
       ); 

Тот же трубопровод используется, если несколько запросов поступают из одного и того же соединения. Request1 может потребоваться Handler1, Request2 может потребоваться Handler2, а Request3 может потребоваться Handler3. Предположим, что запросы поступают как Request1, Request2, Request3. Request1 будет изменять конвейер для добавления Handler1.

  1. В последующих вызовах всегда нужно проверить, изменена ли шифра, а затем удалить нежелательные обработчики? А затем добавьте требуемые обработчики, которые необходимы для обработки этого конкретного вызова?

  2. Или следует удалить обработчик перед тем, как перейти к следующему обработчику (fireChannelRead (object))? Будет ли это иметь влияние на производительность?

  3. Есть ли другой способ сделать это?

Thanks & С уважением,

Tanima

ответ

9

Динамически манипулируя трубопровода является относительно дорогостоящей операцией. Если то, что вы пытаетесь реализовать, это просто простой случай переключения, например делегирование, вы можете написать обработчик, который это делает. Например:

public class SwitchCaseHandler extends ChannelInboundHandlerAdapter { 

    private final ChannelInboundHandler handler1 = ...; 
    private final ChannelInboundHandler handler2 = ...; 
    private final ChannelInboundHandler handler3 = ...; 
    ... 

    @Override 
    public void channelRead(ctx, msg) { 
     if (isForHandler1(msg)) { 
      handler1.channelRead(ctx, msg); 
     } else if (isForHandler2(msg)) { 
      handler2.channelRead(ctx, msg); 
     } ... 
    } 
} 

Пожалуйста, обратите внимание, что handler[1|2|3] не нужно быть ChannelInboundHandler на самом деле. Вместо этого вы можете определить простой интерфейс:

public interface ChannelMessageHandler { 
    void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception; 
} 
Смежные вопросы