Class NettyOptions


  • public class NettyOptions
    extends Object
    A set of hooks that allow clients to customize the driver's underlying Netty layer.

    Clients that need to hook into the driver's underlying Netty layer can subclass this class and provide the necessary customization by overriding its methods.

    Typically, clients would register this class with Cluster.builder():

         NettyOptions nettyOptions = ...
         Cluster cluster = Cluster.builder()
              .addContactPoint(...)
              .withNettyOptions(nettyOptions)
              .build();
     

    Extending the NettyOptions API

    Contrary to other driver options, the options available in this class should be considered as advanced features and as such, they should only be modified by expert users.

    A misconfiguration introduced by the means of this API can have unexpected results and cause the driver to completely fail to connect.

    Moreover, since versions 2.0.9 and 2.1.4 (see JAVA-538), the driver is available in two different flavors: with a standard Maven dependency on Netty, or with a "shaded" (internalized) Netty dependency.

    Given that NettyOptions API exposes Netty classes (SocketChannel, etc.), it should only be extended by clients using the non-shaded version of driver.

    Extending this API with shaded Netty classes is not supported, and in particular for OSGi applications, it is likely that such a configuration would lead to compile and/or runtime errors.

    Since:
    2.0.10
    • Constructor Detail

      • NettyOptions

        public NettyOptions()
    • Method Detail

      • eventLoopGroup

        public EventLoopGroup eventLoopGroup​(ThreadFactory threadFactory)
        Return the EventLoopGroup instance to use.

        This hook is invoked only once at Cluster initialization; the returned instance will be kept in use throughout the cluster lifecycle.

        Typically, implementors would return a newly-created instance; it is however possible to re-use a shared instance, but in this case implementors should also override onClusterClose(EventLoopGroup) to prevent the shared instance to be closed when the cluster is closed.

        The default implementation returns a new instance of io.netty.channel.epoll.EpollEventLoopGroup if epoll is available, or io.netty.channel.nio.NioEventLoopGroup otherwise.

        Parameters:
        threadFactory - The ThreadFactory to use when creating a new EventLoopGroup instance; The driver will provide its own internal thread factory here. It is safe to ignore it and use another thread factory. Note however that for optimal performance it is recommended to use a factory that returns FastThreadLocalThread instances (such as Netty's Executors.DefaultThreadFactory).
        Returns:
        the EventLoopGroup instance to use.
      • channelClass

        public Class<? extends SocketChannel> channelClass()
        Return the specific SocketChannel subclass to use.

        This hook is invoked only once at Cluster initialization; the returned instance will then be used each time the driver creates a new Connection and configures a new instance of Bootstrap for it.

        The default implementation returns io.netty.channel.epoll.EpollSocketChannel if epoll is available, or io.netty.channel.socket.nio.NioSocketChannel otherwise.

        Returns:
        The SocketChannel subclass to use.
      • afterBootstrapInitialized

        public void afterBootstrapInitialized​(Bootstrap bootstrap)
        Hook invoked each time the driver creates a new Connection and configures a new instance of Bootstrap for it.

        This hook is guaranteed to be called after the driver has applied all SocketOptionss.

        This is a good place to add extra ChannelOptions to the boostrap; e.g. plug a custom ByteBufAllocator implementation:

         ByteBufAllocator myCustomByteBufAllocator = ...
        
         public void afterBootstrapInitialized(Bootstrap bootstrap) {
             bootstrap.option(ChannelOption.ALLOCATOR, myCustomByteBufAllocator);
         }
         

        Note that the default implementation of this method configures a pooled ByteBufAllocator (Netty 4.0 defaults to unpooled). If you override this method to set unrelated options, make sure you call super.afterBootstrapInitialized(bootstrap).

        Parameters:
        bootstrap - the Bootstrap being initialized.
      • afterChannelInitialized

        public void afterChannelInitialized​(SocketChannel channel)
                                     throws Exception
        Hook invoked each time the driver creates a new Connection and initializes the channel.

        This hook is guaranteed to be called after the driver has registered all its internal channel handlers, and applied the configured SSLOptions, if any.

        This is a good place to add extra ChannelHandlers to the channel's pipeline; e.g. to add a custom SSL handler to the beginning of the handler chain, do the following:

         ChannelPipeline pipeline = channel.pipeline();
         SSLEngine myCustomSSLEngine = ...
         SslHandler myCustomSSLHandler = new SslHandler(myCustomSSLEngine);
         pipeline.addFirst("ssl", myCustomSSLHandler);
         

        Note: if you intend to provide your own SSL implementation, do not enable the driver's built-in SSLOptions at the same time.

        Parameters:
        channel - the SocketChannel instance, after being initialized by the driver.
        Throws:
        Exception - if this methods encounters any errors.
      • onClusterClose

        public void onClusterClose​(EventLoopGroup eventLoopGroup)
        Hook invoked when the cluster is shutting down after a call to Cluster.close().

        This is guaranteed to be called only after all connections have been individually closed, and their channels closed, and only once per EventLoopGroup instance.

        This gives the implementor a chance to close the EventLoopGroup properly, if required.

        The default implementation initiates a graceful shutdown of the passed EventLoopGroup, then waits uninterruptibly for the shutdown to complete or timeout.

        Implementation note: if the EventLoopGroup instance is being shared, or used for other purposes than to coordinate Netty events for the current cluster, then it should not be shut down here; subclasses would have to override this method accordingly to take the appropriate action.

        Parameters:
        eventLoopGroup - the event loop group used by the cluster being closed
      • timer

        public Timer timer​(ThreadFactory threadFactory)
        Return the Timer instance used by Read Timeouts and Speculative Execution.

        This hook is invoked only once at Cluster initialization; the returned instance will be kept in use throughout the cluster lifecycle.

        Typically, implementors would return a newly-created instance; it is however possible to re-use a shared instance, but in this case implementors should also override onClusterClose(Timer) to prevent the shared instance to be closed when the cluster is closed.

        The default implementation returns a new instance created by HashedWheelTimer(ThreadFactory).

        Parameters:
        threadFactory - The ThreadFactory to use when creating a new HashedWheelTimer instance; The driver will provide its own internal thread factory here. It is safe to ignore it and use another thread factory. Note however that for optimal performance it is recommended to use a factory that returns FastThreadLocalThread instances (such as Netty's Executors.DefaultThreadFactory).
        Returns:
        the Timer instance to use.
      • onClusterClose

        public void onClusterClose​(Timer timer)
        Hook invoked when the cluster is shutting down after a call to Cluster.close().

        This is guaranteed to be called only after all connections have been individually closed, and their channels closed, and only once per Timer instance.

        This gives the implementor a chance to close the Timer properly, if required.

        The default implementation calls a Timer.stop() of the passed Timer instance.

        Implementation note: if the Timer instance is being shared, or used for other purposes than to schedule actions for the current cluster, than it should not be stopped here; subclasses would have to override this method accordingly to take the appropriate action.

        Parameters:
        timer - the timer used by the cluster being closed