Search in sources :

Example 1 with AsyncCloseable

use of io.servicetalk.concurrent.api.AsyncCloseable in project servicetalk by apple.

the class ChannelSet method closeAsyncGracefully.

@Override
public Completable closeAsyncGracefully() {
    return new SubscribableCompletable() {

        @Override
        protected void handleSubscribe(final Subscriber subscriber) {
            if (!stateUpdater.compareAndSet(ChannelSet.this, OPEN, GRACEFULLY_CLOSING)) {
                toSource(onClose).subscribe(subscriber);
                return;
            }
            if (channelMap.isEmpty()) {
                toSource(onClose).subscribe(subscriber);
                onCloseProcessor.onComplete();
                return;
            }
            CompositeCloseable closeable = newCompositeCloseable();
            for (final Channel channel : channelMap.values()) {
                Attribute<PrivilegedListenableAsyncCloseable> closeableAttribute = channel.attr(CHANNEL_CLOSEABLE_KEY);
                PrivilegedListenableAsyncCloseable channelCloseable = closeableAttribute.getAndSet(null);
                if (null != channelCloseable) {
                    // Upon shutdown of the set, we will close all live channels. If close of individual channels
                    // are offloaded, then this would trigger a surge in threads required to offload these closures.
                    // Here we assume that if there is any offloading required, it is done by offloading the
                    // Completable returned by closeAsyncGracefully() hence offloading each channel is not required.
                    // Hence, we use the "noOffload" variant for each channel for this particular subscribe to use
                    // immediate and effectively disable offloading on each channel.
                    closeable.merge(new AsyncCloseable() {

                        @Override
                        public Completable closeAsync() {
                            return channelCloseable.closeAsyncNoOffload();
                        }

                        @Override
                        public Completable closeAsyncGracefully() {
                            return channelCloseable.closeAsyncGracefullyNoOffload();
                        }
                    });
                } else {
                    channel.close();
                }
            }
            closeable.append(() -> onClose);
            toSource(closeable.closeAsyncGracefully()).subscribe(subscriber);
        }
    };
}
Also used : AsyncCloseable(io.servicetalk.concurrent.api.AsyncCloseable) ListenableAsyncCloseable(io.servicetalk.concurrent.api.ListenableAsyncCloseable) SubscribableCompletable(io.servicetalk.concurrent.api.internal.SubscribableCompletable) Completable(io.servicetalk.concurrent.api.Completable) Channel(io.netty.channel.Channel) CompositeCloseable(io.servicetalk.concurrent.api.CompositeCloseable) AsyncCloseables.newCompositeCloseable(io.servicetalk.concurrent.api.AsyncCloseables.newCompositeCloseable) SubscribableCompletable(io.servicetalk.concurrent.api.internal.SubscribableCompletable)

Aggregations

Channel (io.netty.channel.Channel)1 AsyncCloseable (io.servicetalk.concurrent.api.AsyncCloseable)1 AsyncCloseables.newCompositeCloseable (io.servicetalk.concurrent.api.AsyncCloseables.newCompositeCloseable)1 Completable (io.servicetalk.concurrent.api.Completable)1 CompositeCloseable (io.servicetalk.concurrent.api.CompositeCloseable)1 ListenableAsyncCloseable (io.servicetalk.concurrent.api.ListenableAsyncCloseable)1 SubscribableCompletable (io.servicetalk.concurrent.api.internal.SubscribableCompletable)1