4545
4646import java .util .Iterator ;
4747import java .util .NoSuchElementException ;
48+ import java .util .concurrent .BlockingQueue ;
4849import java .util .concurrent .CancellationException ;
4950import java .util .concurrent .ExecutionException ;
5051import java .util .concurrent .Future ;
51- import java .util .concurrent .LinkedBlockingQueue ;
52+ import java .util .concurrent .ArrayBlockingQueue ;
5253import java .util .concurrent .TimeUnit ;
5354
5455/**
@@ -148,7 +149,7 @@ public static <ReqT, RespT> void asyncUnaryCall(
148149 // TODO(lryan): Not clear if we want to use this idiom for 'simple' stubs.
149150 public static <ReqT , RespT > Iterator <RespT > blockingServerStreamingCall (
150151 Call <ReqT , RespT > call , ReqT param ) {
151- BlockingResponseStream <RespT > result = new BlockingResponseStream <RespT >();
152+ BlockingResponseStream <RespT > result = new BlockingResponseStream <RespT >(call );
152153 asyncServerStreamingCall (call , param , result .listener ());
153154 return result ;
154155 }
@@ -331,11 +332,17 @@ public void onClose(Status status, Metadata.Trailers trailers) {
331332 */
332333 // TODO(ejona): determine how to allow Call.cancel() in case of application error.
333334 private static class BlockingResponseStream <T > implements Iterator <T > {
334- private final LinkedBlockingQueue <Object > buffer = new LinkedBlockingQueue <Object >();
335+ // Due to flow control, only needs to hold up to 2 items: 1 for value, 1 for close.
336+ private final BlockingQueue <Object > buffer = new ArrayBlockingQueue <Object >(2 );
335337 private final Call .Listener <T > listener = new QueuingListener ();
338+ private final Call <?, T > call ;
336339 // Only accessed when iterating.
337340 private Object last ;
338341
342+ private BlockingResponseStream (Call <?, T > call ) {
343+ this .call = call ;
344+ }
345+
339346 Call .Listener <T > listener () {
340347 return listener ;
341348 }
@@ -362,6 +369,7 @@ public T next() {
362369 throw new NoSuchElementException ();
363370 }
364371 try {
372+ call .request (1 );
365373 @ SuppressWarnings ("unchecked" )
366374 T tmp = (T ) last ;
367375 return tmp ;
0 commit comments