Top Description Inners Fields Constructors Methods
io.netty5.handler.flow

public Class FlowControlHandler

extends Object
implements ChannelHandler
Class Inheritance
All Implemented Interfaces
io.netty5.channel.ChannelHandler
Imports
io.netty5.channel.ChannelOption, .ReadBufferAllocator, .ChannelHandler, .ChannelHandlerContext, io.netty5.handler.codec.ByteToMessageDecoder, .MessageToByteEncoder, io.netty5.util.Resource, io.netty5.util.internal.ObjectPool, .ObjectPool.Handle, io.netty5.util.internal.logging.InternalLogger, .InternalLoggerFactory, java.util.ArrayDeque, .Queue

The FlowControlHandler ensures that only one message per read() is sent downstream. Classes such as ByteToMessageDecoder or MessageToByteEncoder are free to emit as many events as they like for any given input. A channel's auto reading configuration doesn't usually apply in these scenarios. This is causing problems in downstream ChannelHandlers that would like to hold subsequent events while they're processing one event. It's a common problem with the HttpObjectDecoder that will very often fire an HttpRequest that is immediately followed by a LastHttpContent event.
ChannelPipeline pipeline = ...;

pipeline.addLast(new HttpServerCodec());
pipeline.addLast(new FlowControlHandler());

pipeline.addLast(new MyExampleHandler());

class MyExampleHandler extends ChannelInboundHandlerAdapter {
  @Override
  public void channelRead(ChannelHandlerContext ctx, Object msg) {
    if (msg instanceof HttpRequest) {
      ctx.channel().setChannelOption(ChannelOption.AUTO_READ, false);

      // The FlowControlHandler will hold any subsequent events that
      // were emitted by HttpObjectDecoder until auto reading is turned
      // back on or Channel#read() is being called.
    }
  }
}
See Also
ChannelOption#AUTO_READ)

Nested and Inner Type Summary

Modifier and TypeClass and Description
private static class

Field Summary

Modifier and TypeField and Description
private static final InternalLogger
private FlowControlHandler.RecyclableArrayDeque
private final boolean
private boolean

Constructor Summary

AccessConstructor and Description
public
public
FlowControlHandler(boolean releaseMessages)

Method Summary

Modifier and TypeMethod and Description
public void
channelInactive(ChannelHandlerContext ctx)

Overrides default io.netty5.channel.ChannelHandler.channelInactive.

The Channel of the ChannelHandlerContext was registered is now inactive and reached its end of lifetime.
public void
channelRead(ChannelHandlerContext ctx, Object msg)

Overrides default io.netty5.channel.ChannelHandler.channelRead.

Invoked when the current Channel has read a message from the peer.
public void
channelReadComplete(ChannelHandlerContext ctx)

Overrides default io.netty5.channel.ChannelHandler.channelReadComplete.

Invoked when the last message read by the current read operation has been consumed by channelRead(ChannelHandlerContext, Object).
private int
dequeue(ChannelHandlerContext ctx, int minConsume)

Dequeues one or many (or none) messages depending on the channel's auto reading state and returns the number of messages that were consumed from the internal queue.

private void
destroy()

Releases all messages and destroys the Queue.

public void
handlerRemoved(ChannelHandlerContext ctx)

Overrides default io.netty5.channel.ChannelHandler.handlerRemoved.

Gets called after the ChannelHandler was removed from the actual context and it doesn't handle events anymore.
pack-priv boolean
isQueueEmpty()

Determine if the underlying Queue is empty.

public void
read(ChannelHandlerContext
the ChannelHandlerContext for which the read operation is made
ctx
,
ReadBufferAllocator
The ReadBufferAllocator that should be used to allocate a Buffer if needed (for reading the data).
readBufferAllocator
)

Overrides default io.netty5.channel.ChannelHandler.read.

Called once a read operation is made from the current registered EventLoop.
Inherited from java.lang.Object:
cloneequalsfinalizegetClasshashCodenotifynotifyAlltoStringwaitwaitwait

Field Detail

loggerback to summary
private static final InternalLogger logger
queueback to summary
private FlowControlHandler.RecyclableArrayDeque queue
releaseMessagesback to summary
private final boolean releaseMessages
shouldConsumeback to summary
private boolean shouldConsume

Constructor Detail

FlowControlHandlerback to summary
public FlowControlHandler()
FlowControlHandlerback to summary
public FlowControlHandler(boolean releaseMessages)

Method Detail

channelInactiveback to summary
public void channelInactive(ChannelHandlerContext ctx) throws Exception

Overrides default io.netty5.channel.ChannelHandler.channelInactive.

Doc from io.netty5.channel.ChannelHandler.channelInactive.

The Channel of the ChannelHandlerContext was registered is now inactive and reached its end of lifetime.

Annotations
@Override
channelReadback to summary
public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception

Overrides default io.netty5.channel.ChannelHandler.channelRead.

Doc from io.netty5.channel.ChannelHandler.channelRead.

Invoked when the current Channel has read a message from the peer.

Annotations
@Override
channelReadCompleteback to summary
public void channelReadComplete(ChannelHandlerContext ctx) throws Exception

Overrides default io.netty5.channel.ChannelHandler.channelReadComplete.

Doc from io.netty5.channel.ChannelHandler.channelReadComplete.

Invoked when the last message read by the current read operation has been consumed by channelRead(ChannelHandlerContext, Object). If ChannelOption#AUTO_READ is off, no further attempt to read an inbound data from the current Channel will be made until ChannelOutboundInvoker#read(ReadBufferAllocator) is called.

Annotations
@Override
dequeueback to summary
private int dequeue(ChannelHandlerContext ctx, int minConsume)

Dequeues one or many (or none) messages depending on the channel's auto reading state and returns the number of messages that were consumed from the internal queue. The minConsume argument is used to force dequeue() into consuming that number of messages regardless of the channel's auto reading configuration.

See Also
ChannelHandler#read(ChannelHandlerContext, ReadBufferAllocator), channelRead(ChannelHandlerContext, Object)
destroyback to summary
private void destroy()

Releases all messages and destroys the Queue.

handlerRemovedback to summary
public void handlerRemoved(ChannelHandlerContext ctx) throws Exception

Overrides default io.netty5.channel.ChannelHandler.handlerRemoved.

Doc from io.netty5.channel.ChannelHandler.handlerRemoved.

Gets called after the ChannelHandler was removed from the actual context and it doesn't handle events anymore.

Annotations
@Override
isQueueEmptyback to summary
pack-priv boolean isQueueEmpty()

Determine if the underlying Queue is empty. This method exists for testing, debugging and inspection purposes and it is not Thread safe!

readback to summary
public void read(ChannelHandlerContext ctx, ReadBufferAllocator readBufferAllocator)

Overrides default io.netty5.channel.ChannelHandler.read.

Doc from io.netty5.channel.ChannelHandler.read.

Called once a read operation is made from the current registered EventLoop. If the ChannelHandler implementation queues the read and another read happens it is free to drop the first ReadBufferAllocator and just use the last one.

Parameters
ctx:ChannelHandlerContext

the ChannelHandlerContext for which the read operation is made

readBufferAllocator:ReadBufferAllocator

The ReadBufferAllocator that should be used to allocate a Buffer if needed (for reading the data).

Annotations
@Override
io.netty5.handler.flow back to summary

private final Class FlowControlHandler.RecyclableArrayDeque

extends ArrayDeque<Object>
Class Inheritance

A recyclable ArrayDeque.

Field Summary

Modifier and TypeField and Description
private static final int
DEFAULT_NUM_ELEMENTS

A value of 2 should be a good choice for most scenarios.

private final ObjectPool.Handle<FlowControlHandler.RecyclableArrayDeque>
private static final ObjectPool<FlowControlHandler.RecyclableArrayDeque>
private static final long

Constructor Summary

AccessConstructor and Description
private

Method Summary

Modifier and TypeMethod and Description
public static FlowControlHandler.RecyclableArrayDeque
public void
Inherited from java.util.ArrayDeque:
addaddAlladdFirstaddLastclearclonecontainsdescendingIteratorelementforEachgetFirstgetLastisEmptyiteratorofferofferFirstofferLastpeekpeekFirstpeekLastpollpollFirstpollLastpoppushremoveremoveremoveAllremoveFirstremoveFirstOccurrenceremoveIfremoveLastremoveLastOccurrenceretainAllsizespliteratortoArraytoArray

Field Detail

DEFAULT_NUM_ELEMENTSback to summary
private static final int DEFAULT_NUM_ELEMENTS

A value of 2 should be a good choice for most scenarios.

handleback to summary
private final ObjectPool.Handle<FlowControlHandler.RecyclableArrayDeque> handle
RECYCLERback to summary
private static final ObjectPool<FlowControlHandler.RecyclableArrayDeque> RECYCLER
serialVersionUIDback to summary
private static final long serialVersionUID

Hides java.util.ArrayDeque.serialVersionUID.

Constructor Detail

RecyclableArrayDequeback to summary
private RecyclableArrayDeque(int numElements, ObjectPool.Handle<FlowControlHandler.RecyclableArrayDeque> handle)

Method Detail

newInstanceback to summary
public static FlowControlHandler.RecyclableArrayDeque newInstance()
recycleback to summary
public void recycle()