Class LoadBalancer.PickResult
- java.lang.Object
-
- io.grpc.LoadBalancer.PickResult
-
- Enclosing class:
- LoadBalancer
@Immutable @ExperimentalApi("https://github.com/grpc/grpc-java/issues/1771") public static final class LoadBalancer.PickResult extends Object
A balancing decision made bySubchannelPicker
for an RPC.The outcome of the decision will be one of the following:
- Proceed: if a Subchannel is provided via
withSubchannel()
, and is in READY state when the RPC tries to start on it, the RPC will proceed on that Subchannel. - Error: if an error is provided via
withError()
, and the RPC is not wait-for-ready (i.e.,CallOptions.withWaitForReady()
was not called), the RPC will fail immediately with the given error. - Buffer: in all other cases, the RPC will be buffered in the Channel, until the next
picker is provided via
Helper.updateBalancingState()
, when the RPC will go through the same picking process again.
- Since:
- 1.2.0
-
-
Method Summary
All Methods Static Methods Instance Methods Concrete Methods Modifier and Type Method Description boolean
equals(Object other)
String
getAuthorityOverride()
Returns the authority override if any.Status
getStatus()
The status associated with this result.ClientStreamTracer.Factory
getStreamTracerFactory()
The stream tracer factory this result was created with.LoadBalancer.Subchannel
getSubchannel()
The Subchannel if this result was created bywithSubchannel()
, or null otherwise.int
hashCode()
boolean
hasResult()
Returnstrue
if the pick was not created withwithNoResult()
.boolean
isDrop()
Returnstrue
if this result was created bywithDrop()
.String
toString()
static LoadBalancer.PickResult
withDrop(Status status)
A decision to fail an RPC immediately.static LoadBalancer.PickResult
withError(Status error)
A decision to report a connectivity error to the RPC.static LoadBalancer.PickResult
withNoResult()
No decision could be made.static LoadBalancer.PickResult
withSubchannel(LoadBalancer.Subchannel subchannel)
Equivalent towithSubchannel(subchannel, null)
.static LoadBalancer.PickResult
withSubchannel(LoadBalancer.Subchannel subchannel, ClientStreamTracer.Factory streamTracerFactory)
A decision to proceed the RPC on a Subchannel.static LoadBalancer.PickResult
withSubchannel(LoadBalancer.Subchannel subchannel, ClientStreamTracer.Factory streamTracerFactory, String authorityOverride)
Same aswithSubchannel(subchannel, streamTracerFactory)
but with an authority name to override in the host header.
-
-
-
Method Detail
-
withSubchannel
public static LoadBalancer.PickResult withSubchannel(LoadBalancer.Subchannel subchannel, @Nullable ClientStreamTracer.Factory streamTracerFactory)
A decision to proceed the RPC on a Subchannel.The Subchannel should either be an original Subchannel returned by
Helper.createSubchannel()
, or a wrapper of it preferably based onForwardingSubchannel
. At the very least itsgetInternalSubchannel()
must return the same object as the one returned by the original. Otherwise the Channel cannot use it for the RPC.When the RPC tries to use the return Subchannel, which is briefly after this method returns, the state of the Subchannel will decide where the RPC would go:
- READY: the RPC will proceed on this Subchannel.
- IDLE: the RPC will be buffered. Subchannel will attempt to create connection.
- All other states: the RPC will be buffered.
All buffered RPCs will stay buffered until the next call of
Helper.updateBalancingState()
, which will trigger a new picking process.Note that Subchannel's state may change at the same time the picker is making the decision, which means the decision may be made with (to-be) outdated information. For example, a picker may return a Subchannel known to be READY, but it has become IDLE when is about to be used by the RPC, which makes the RPC to be buffered. The LoadBalancer will soon learn about the Subchannels' transition from READY to IDLE, create a new picker and allow the RPC to use another READY transport if there is any.
You will want to avoid running into a situation where there are READY Subchannels out there but some RPCs are still buffered for longer than a brief time.
- This can happen if you return Subchannels with states other than READY and IDLE. For example, suppose you round-robin on 2 Subchannels, in READY and CONNECTING states respectively. If the picker ignores the state and pick them equally, 50% of RPCs will be stuck in buffered state until both Subchannels are READY.
- This can also happen if you don't create a new picker at key state changes of Subchannels. Take the above round-robin example again. Suppose you do pick only READY and IDLE Subchannels, and initially both Subchannels are READY. Now one becomes IDLE, then CONNECTING and stays CONNECTING for a long time. If you don't create a new picker in response to the CONNECTING state to exclude that Subchannel, 50% of RPCs will hit it and be buffered even though the other Subchannel is READY.
In order to prevent unnecessary delay of RPCs, the rules of thumb are:
- The picker should only pick Subchannels that are known as READY or IDLE. Whether to
pick IDLE Subchannels depends on whether you want Subchannels to connect on-demand or
actively:
- If you want connect-on-demand, include IDLE Subchannels in your pick results, because when an RPC tries to use an IDLE Subchannel, the Subchannel will try to connect.
- If you want Subchannels to be always connected even when there is no RPC, you
would call
Subchannel.requestConnection()
whenever the Subchannel has transitioned to IDLE, then you don't need to include IDLE Subchannels in your pick results.
- Always create a new picker and call
Helper.updateBalancingState()
wheneverhandleSubchannelState()
is called, unless the new state is SHUTDOWN. SeehandleSubchannelState
's javadoc for more details.
- Parameters:
subchannel
- the picked Subchannel. It must have beenstarted
streamTracerFactory
- if not null, will be used to trace the activities of the stream created as a result of this pick. Note it's possible that no stream is created at all in some cases.- Since:
- 1.3.0
-
withSubchannel
@ExperimentalApi("https://github.com/grpc/grpc-java/issues/11656") public static LoadBalancer.PickResult withSubchannel(LoadBalancer.Subchannel subchannel, @Nullable ClientStreamTracer.Factory streamTracerFactory, @Nullable String authorityOverride)
Same aswithSubchannel(subchannel, streamTracerFactory)
but with an authority name to override in the host header.
-
withSubchannel
public static LoadBalancer.PickResult withSubchannel(LoadBalancer.Subchannel subchannel)
Equivalent towithSubchannel(subchannel, null)
.- Since:
- 1.2.0
-
withError
public static LoadBalancer.PickResult withError(Status error)
A decision to report a connectivity error to the RPC. If the RPC iswait-for-ready
, it will stay buffered. Otherwise, it will fail with the given error.- Parameters:
error
- the error status. Must not be OK.- Since:
- 1.2.0
-
withDrop
public static LoadBalancer.PickResult withDrop(Status status)
A decision to fail an RPC immediately. This is a final decision and will ignore retry policy.- Parameters:
status
- the status with which the RPC will fail. Must not be OK.- Since:
- 1.8.0
-
withNoResult
public static LoadBalancer.PickResult withNoResult()
No decision could be made. The RPC will stay buffered.- Since:
- 1.2.0
-
getAuthorityOverride
@ExperimentalApi("https://github.com/grpc/grpc-java/issues/11656") @Nullable public String getAuthorityOverride()
Returns the authority override if any.
-
getSubchannel
@Nullable public LoadBalancer.Subchannel getSubchannel()
The Subchannel if this result was created bywithSubchannel()
, or null otherwise.- Since:
- 1.2.0
-
getStreamTracerFactory
@Nullable public ClientStreamTracer.Factory getStreamTracerFactory()
The stream tracer factory this result was created with.- Since:
- 1.3.0
-
getStatus
public Status getStatus()
- Since:
- 1.2.0
-
isDrop
public boolean isDrop()
Returnstrue
if this result was created bywithDrop()
.- Since:
- 1.8.0
-
hasResult
public boolean hasResult()
Returnstrue
if the pick was not created withwithNoResult()
.
-
-