Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
/*
* Copyright 2016, gRPC Authors All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package nl.topicus.jdbc.shaded.io.grpc.internal;
import static nl.topicus.jdbc.shaded.com.google.common.base.Preconditions.checkArgument;
import static nl.topicus.jdbc.shaded.com.google.common.base.Preconditions.checkNotNull;
import static nl.topicus.jdbc.shaded.com.google.common.base.Preconditions.checkState;
import static nl.topicus.jdbc.shaded.io.grpc.ConnectivityState.IDLE;
import static nl.topicus.jdbc.shaded.io.grpc.ConnectivityState.SHUTDOWN;
import static nl.topicus.jdbc.shaded.io.grpc.ConnectivityState.TRANSIENT_FAILURE;
import nl.topicus.jdbc.shaded.com.google.common.annotations.VisibleForTesting;
import nl.topicus.jdbc.shaded.com.google.common.base.Stopwatch;
import nl.topicus.jdbc.shaded.com.google.common.base.Supplier;
import nl.topicus.jdbc.shaded.com.google.common.util.concurrent.ListenableFuture;
import nl.topicus.jdbc.shaded.com.google.common.util.concurrent.SettableFuture;
import nl.topicus.jdbc.shaded.io.grpc.Attributes;
import nl.topicus.jdbc.shaded.io.grpc.CallOptions;
import nl.topicus.jdbc.shaded.io.grpc.Channel;
import nl.topicus.jdbc.shaded.io.grpc.ClientCall;
import nl.topicus.jdbc.shaded.io.grpc.ClientInterceptor;
import nl.topicus.jdbc.shaded.io.grpc.ClientInterceptors;
import nl.topicus.jdbc.shaded.io.grpc.CompressorRegistry;
import nl.topicus.jdbc.shaded.io.grpc.ConnectivityState;
import nl.topicus.jdbc.shaded.io.grpc.ConnectivityStateInfo;
import nl.topicus.jdbc.shaded.io.grpc.Context;
import nl.topicus.jdbc.shaded.io.grpc.DecompressorRegistry;
import nl.topicus.jdbc.shaded.io.grpc.EquivalentAddressGroup;
import nl.topicus.jdbc.shaded.io.grpc.InternalChannelStats;
import nl.topicus.jdbc.shaded.io.grpc.InternalInstrumented;
import nl.topicus.jdbc.shaded.io.grpc.InternalLogId;
import nl.topicus.jdbc.shaded.io.grpc.LoadBalancer;
import nl.topicus.jdbc.shaded.io.grpc.LoadBalancer.PickResult;
import nl.topicus.jdbc.shaded.io.grpc.LoadBalancer.PickSubchannelArgs;
import nl.topicus.jdbc.shaded.io.grpc.LoadBalancer.SubchannelPicker;
import nl.topicus.jdbc.shaded.io.grpc.ManagedChannel;
import nl.topicus.jdbc.shaded.io.grpc.Metadata;
import nl.topicus.jdbc.shaded.io.grpc.MethodDescriptor;
import nl.topicus.jdbc.shaded.io.grpc.NameResolver;
import nl.topicus.jdbc.shaded.io.grpc.Status;
import nl.topicus.jdbc.shaded.io.grpc.internal.ClientCallImpl.ClientTransportProvider;
import java.lang.ref.Reference;
import java.lang.ref.ReferenceQueue;
import java.lang.ref.SoftReference;
import java.lang.ref.WeakReference;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.Executor;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.logging.Level;
import java.util.logging.LogRecord;
import java.util.logging.Logger;
import java.util.regex.Pattern;
import nl.topicus.jdbc.shaded.javax.annotation.Nullable;
import nl.topicus.jdbc.shaded.javax.annotation.concurrent.GuardedBy;
import nl.topicus.jdbc.shaded.javax.annotation.concurrent.ThreadSafe;
/** A communication channel for making outgoing RPCs. */
@ThreadSafe
public final class ManagedChannelImpl
extends ManagedChannel implements InternalInstrumented {
static final Logger logger = Logger.getLogger(ManagedChannelImpl.class.getName());
// Matching this pattern means the target string is a URI target or at least intended to be one.
// A URI target must be an absolute hierarchical URI.
// From RFC 2396: scheme = alpha *( alpha | digit | "+" | "-" | "." )
@VisibleForTesting
static final Pattern URI_PATTERN = Pattern.compile("[a-zA-Z][a-zA-Z0-9+.-]*:/.*");
static final long IDLE_TIMEOUT_MILLIS_DISABLE = -1;
@VisibleForTesting
static final long SUBCHANNEL_SHUTDOWN_DELAY_SECONDS = 5;
@VisibleForTesting
static final Status SHUTDOWN_NOW_STATUS =
Status.UNAVAILABLE.withDescription("Channel shutdownNow invoked");
@VisibleForTesting
static final Status SHUTDOWN_STATUS =
Status.UNAVAILABLE.withDescription("Channel shutdown invoked");
@VisibleForTesting
static final Status SUBCHANNEL_SHUTDOWN_STATUS =
Status.UNAVAILABLE.withDescription("Subchannel shutdown invoked");
private final InternalLogId logId = InternalLogId.allocate(getClass().getName());
private final String target;
private final NameResolver.Factory nameResolverFactory;
private final Attributes nameResolverParams;
private final LoadBalancer.Factory loadBalancerFactory;
private final ClientTransportFactory transportFactory;
private final Executor executor;
private final ObjectPool extends Executor> executorPool;
private final ObjectPool extends Executor> oobExecutorPool;
private final ChannelExecutor channelExecutor = new ChannelExecutor();
private boolean fullStreamDecompression;
private final DecompressorRegistry decompressorRegistry;
private final CompressorRegistry compressorRegistry;
private final Supplier stopwatchSupplier;
/** The timout before entering idle mode. */
private final long idleTimeoutMillis;
private final ConnectivityStateManager channelStateManager = new ConnectivityStateManager();
private final BackoffPolicy.Provider backoffPolicyProvider;
/**
* We delegate to this channel, so that we can have interceptors as necessary. If there aren't
* any interceptors this will just be {@link RealChannel}.
*/
private final Channel interceptorChannel;
@Nullable private final String userAgent;
// Only null after channel is terminated. Must be assigned from the channelExecutor.
private NameResolver nameResolver;
private final ProxyDetector proxyDetector;
// Must be accessed from the channelExecutor.
private boolean nameResolverStarted;
// null when channel is in idle mode. Must be assigned from channelExecutor.
@Nullable
private LbHelperImpl lbHelper;
// Must be assigned from channelExecutor. null if channel is in idle mode.
@Nullable
private volatile SubchannelPicker subchannelPicker;
// Must be mutated from channelExecutor
// If any monitoring hook to be added later needs to get a snapshot of this Set, we could
// switch to a ConcurrentHashMap.
private final Set subchannels = new HashSet(16, .75f);
// Must be mutated from channelExecutor
private final Set oobChannels = new HashSet(1, .75f);
// reprocess() must be run from channelExecutor
private final DelayedClientTransport delayedTransport;
// Shutdown states.
//
// Channel's shutdown process:
// 1. shutdown(): stop accepting new calls from applications
// 1a shutdown <- true
// 1b subchannelPicker <- null
// 1c delayedTransport.shutdown()
// 2. delayedTransport terminated: stop stream-creation functionality
// 2a terminating <- true
// 2b loadBalancer.shutdown()
// * LoadBalancer will shutdown subchannels and OOB channels
// 2c loadBalancer <- null
// 2d nameResolver.shutdown()
// 2e nameResolver <- null
// 3. All subchannels and OOB channels terminated: Channel considered terminated
private final AtomicBoolean shutdown = new AtomicBoolean(false);
// Must only be mutated and read from channelExecutor
private boolean shutdownNowed;
// Must be mutated from channelExecutor
private volatile boolean terminating;
// Must be mutated from channelExecutor
private volatile boolean terminated;
private final CountDownLatch terminatedLatch = new CountDownLatch(1);
private final ManagedChannelReference phantom;
private final ChannelTracer.Factory channelTracerFactory; // new tracer for each oobchannel
private final ChannelTracer channelTracer;
// Called from channelExecutor
private final ManagedClientTransport.Listener delayedTransportListener =
new ManagedClientTransport.Listener() {
@Override
public void transportShutdown(Status s) {
checkState(shutdown.get(), "Channel must have been shut down");
}
@Override
public void transportReady() {
// Don't care
}
@Override
public void transportInUse(final boolean inUse) {
inUseStateAggregator.updateObjectInUse(delayedTransport, inUse);
}
@Override
public void transportTerminated() {
checkState(shutdown.get(), "Channel must have been shut down");
terminating = true;
if (lbHelper != null) {
lbHelper.lb.shutdown();
lbHelper = null;
}
if (nameResolver != null) {
nameResolver.shutdown();
nameResolver = null;
nameResolverStarted = false;
}
// Until LoadBalancer is shutdown, it may still create new subchannels. We catch them
// here.
maybeShutdownNowSubchannels();
maybeTerminateChannel();
}
};
// Must be called from channelExecutor
private void maybeShutdownNowSubchannels() {
if (shutdownNowed) {
for (InternalSubchannel subchannel : subchannels) {
subchannel.shutdownNow(SHUTDOWN_NOW_STATUS);
}
for (InternalSubchannel oobChannel : oobChannels) {
oobChannel.shutdownNow(SHUTDOWN_NOW_STATUS);
}
}
}
// Must be accessed from channelExecutor
@VisibleForTesting
final InUseStateAggregator