Las llamadas de transmisión permiten patrones de interacción más complejos que las solicitudes y respuestas simples, lo que permite enviar o recibir varios mensajes a través de una sola conexión.
Las bibliotecas cliente de Cloud para Java admiten tres tipos de llamadas de transmisión:
- Transmisión desde el servidor: El servidor te envía una transmisión de respuestas.
- Transmisión del cliente: Envías una transmisión de solicitudes al servidor.
- Transmisión bidireccional: Puedes enviar un flujo de solicitudes al servidor, y el servidor puede devolverte un flujo de respuestas.
Las implementaciones de transmisión se modelan según las implementaciones de gRPC-Java para la transmisión bidireccional, del cliente y del servidor.
Compatibilidad con la transmisión en todos los transportes
La transmisión es totalmente compatible cuando se usa gRPC, pero solo parcialmente compatible con HttpJson. Consulta la siguiente tabla para obtener información sobre la compatibilidad con la transmisión.
| Tipo de transmisión | gRPC | HttpJson |
|---|---|---|
| Transmisión desde el servidor | Compatible | Compatible |
| Transmisión para clientes | Compatible | No compatible |
| Transmisión bidireccional | Compatible | No compatible |
Se admiten llamadas unarias (sin transmisión) para gRPC y HttpJson.
Cómo determinar el tipo de transmisión
Para determinar el tipo de transmisión de la llamada, verifica el tipo Callable que se devolvió:
ServerStreamingCallable: Transmisión desde el servidor.ClientStreamingCallable: Transmisión del cliente.BidiStreamingCallable: Transmisión bidireccional.
Por ejemplo, para usar Java-Aiplatform y Java-Speech, haz lo siguiente:
// Server Streaming
ServerStreamingCallable<ReadTensorboardBlobDataRequest, ReadTensorboardBlobDataResponse> callable = aiplatformClient.readTensorboardBlobDataCallable();
// Bidirectional Streaming
BidiStreamingCallable<StreamingRecognizeRequest, StreamingRecognizeResponse> callable = speechClient.streamingRecognizeCallable();
Cómo realizar llamadas de transmisión
La forma de hacer una llamada de transmisión variará según si usas la transmisión del servidor o la transmisión bidireccional.
Transmisión del servidor
La transmisión por servidor no requiere implementación adicional. La clase ServerStream te permite iterar el flujo de respuestas. Si usamos Java-Maps-Routing como ejemplo, a continuación, se muestra cómo llamar a la API de transmisión por servidor:
try (RoutesClient routesClient = RoutesClient.create()) {
ServerStreamingCallable<ComputeRouteMatrixRequest, RouteMatrixElement> computeRouteMatrix =
routesClient.computeRouteMatrixCallable();
ServerStream<RouteMatrixElement> stream = computeRouteMatrix.call(
ComputeRouteMatrixRequest.newBuilder().build());
for (RouteMatrixElement element : stream) {
// Do something with response
}
}
En este ejemplo, el cliente envía un solo ComputeRouteMatrixRequest y recibe un flujo de respuestas.
Transmisión bidireccional
La transmisión bidireccional requiere una implementación adicional para realizar la llamada. Si se usa Java-Speech como ejemplo, los siguientes pasos proporcionan una implementación de ejemplo para realizar una llamada de transmisión bidireccional.
Primero, implementa la interfaz ResponseObserver con el siguiente código como guía:
class BidiResponseObserver<T> implements ResponseObserver<T> {
private final List<T> responses = new ArrayList<>();
private final SettableApiFuture<List<T>> future = SettableApiFuture.create();
@Override
public void onStart(StreamController controller) {
// no-op
}
@Override
public void onResponse(T response) {
responses.add(response);
}
@Override
public void onError(Throwable t) {
future.setException(t);
}
@Override
public void onComplete() {
future.set(responses);
}
public SettableApiFuture<List<T>> getFuture() {
return future;
}
}
Luego, sigue estos pasos:
- Crea una instancia del observador:
java BidiResponseObserver<StreamingRecognizeResponse> responseObserver = new BidiResponseObserver<>(); - Pasa el observador al objeto invocable:
java ClientStream<EchoRequest> clientStream = speechClient.streamingRecognizeCallable().splitCall(responseObserver); - Envía las solicitudes al servidor y cierra la transmisión cuando se complete:
java clientStream.send(StreamingRecognizeRequest.newBuilder().build()); clientStream.send(StreamingRecognizeRequest.newBuilder().build()); // ... other requests ... clientStream.send(StreamingRecognizeRequest.newBuilder().build()); clientStream.closeSend(); Itera a través de las respuestas: ```java List
responses = responseObserver.getFuture().get(); for (StreamingRecognizeResponse response : responses) { // Do something with response } ```
Errores de transmisión no admitidos
En el caso de las bibliotecas cliente que admiten transportes de gRPC y HTTP/JSON, es posible configurar accidentalmente la biblioteca cliente para invocar una llamada de transmisión no admitida. Por ejemplo, la siguiente configuración muestra el cliente HttpJson de Java-Speech que realiza una llamada de transmisión bidireccional:
// SpeechClient is configured to use HttpJson
try (SpeechClient speechClient = SpeechClient.create(SpeechSettings.newHttpJsonBuilder().build())) {
// Bidi Callable is not supported in HttpJson
BidiStreamingCallable<StreamingRecognizeRequest, StreamingRecognizeResponse> callable = speechClient.streamingRecognizeCallable();
...
}
Esto no genera un error de compilación, pero aparece como un error de tiempo de ejecución:
Not implemented: streamingRecognizeCallable(). REST transport is not implemented for this method yet.
Important: The client library MUST be configured with gRPC to use client or bidirectional streaming.