import static java.util.Objects.requireNonNull;
-import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
import io.netty.bootstrap.Bootstrap;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
ReconnectPromise(final EventExecutor executor, final AbstractNetconfDispatcher<S, L> dispatcher,
final InetSocketAddress address, final ReconnectStrategyFactory connectStrategyFactory,
- final Bootstrap bootstrap, final AbstractNetconfDispatcher.PipelineInitializer<S> initializer) {
+ final Bootstrap bootstrap, final PipelineInitializer<S> initializer) {
super(executor);
this.firstSessionFuture = new DefaultPromise<>(executor);
this.bootstrap = requireNonNull(bootstrap);
@Holding("this")
private void lockedConnect() {
- final ReconnectStrategy cs = this.strategyFactory.createReconnectStrategy();
+ final ReconnectStrategy cs = strategyFactory.createReconnectStrategy();
// Set up a client with pre-configured bootstrap, but add a closed channel handler into the pipeline to support
// reconnect attempts
- pending = this.dispatcher.createClient(this.address, cs, bootstrap, (channel, promise) -> {
+ pending = dispatcher.createClient(address, cs, bootstrap, (channel, promise) -> {
initializer.initializeChannel(channel, promise);
// add closed channel handler
// This handler has to be added as last channel handler and the channel inactive event has to be caught by
// reconnect will not work
// This handler is last so all handlers in front of it can handle channel inactive (to e.g. resource
// cleanup) before a new connection is started
- channel.pipeline().addLast(new ClosedChannelHandler(ReconnectPromise.this));
+ channel.pipeline().addLast(inboundHandler);
});
if (!firstSessionFuture.isDone()) {
});
}
}
-
- /**
- * Indicate if the initial connection succeeded.
- *
- * @return true if initial connection was established successfully, false if initial connection failed due to e.g.
- * Connection refused, Negotiation failed
- */
- @SuppressFBWarnings(value = "UPM_UNCALLED_PRIVATE_METHOD",
- justification = "https://github.com/spotbugs/spotbugs/issues/811")
- private synchronized boolean isInitialConnectFinished() {
- requireNonNull(pending);
- return pending.isDone() && pending.isSuccess();
- }
-
- /**
- * Channel handler that responds to channelInactive event and reconnects the session.
- * Only if the promise was not canceled.
- */
- private static final class ClosedChannelHandler extends ChannelInboundHandlerAdapter {
- private final ReconnectPromise<?, ?> promise;
-
- ClosedChannelHandler(final ReconnectPromise<?, ?> promise) {
- this.promise = promise;
- }
-
- @Override
- public void channelInactive(final ChannelHandlerContext ctx) {
- // This is the ultimate channel inactive handler, not forwarding
- if (promise.isCancelled()) {
- return;
- }
-
- if (promise.isInitialConnectFinished() == false) {
- LOG.debug("Connection to {} was dropped during negotiation, reattempting", promise.address);
- }
-
- LOG.debug("Reconnecting after connection to {} was dropped", promise.address);
- promise.connect();
- }
- }
}