Tradias/asio-grpc

GRPC_CALL_ERROR_TOO_MANY_OPERATIONS Error on Concurrent Write Operations

Closed this issue · 3 comments

szanna commented

Hello,

I am facing an issue with a service where multiple clients are connecting and the server is sending data to all of them. Here is a brief outline of my service definition:

service StreamService {
  rpc Connect(ConnectRequest) returns (stream Data);
}

In my code, I have a handler which looks like this:

auto [channel1, channel2] = observers.addObserver(co_await asio::this_coro::executor);
auto [a, b] = co_await (myWriter(writer, channel1) && myWriter(writer, channel2));

The same myWriter function is used twice because each receives different types of data from different asio::channel, but they are going to the same stream Response. The

Here is the myWriter function:

const auto [data] = co_await channel.async_receive(...);
bool ok = co_await agrpc::write(writer, data);

However, I am getting a GRPC_CALL_ERROR_TOO_MANY_OPERATIONS error.

As I understand it, for a single client connection, gRPC can't send another message until the previous one is finished. In that case, does asio-grpc, specifically agrpc::write, handle this issue on its own? If so, where else should I look for a problem if I am incorrectly using asio-grpc?

Additionally, I am curious if there is a function available that checks whether a stream is in progress. This could be helpful in understanding how this error situation occurred.

I appreciate any help or guidance you can provide. Thank you for your time.

Best regards,

Hi,

thanks for the detailed error report. You are correct, gRPC does not support sending another message until the previous one is finished and neither does asio-grpc. agrpc::write is just a thin wrapper around grpc::ServerAsyncWriter.Write(). The same limitations apply. They are also documented https://tradias.github.io/asio-grpc/structagrpc_1_1detail_1_1_write_fn.html#a87ab5914b5bac633e1cdb3798ba85e6e (which is essentially just a copy of the official gRPC documentation).
You have to synchronize the writes yourself, either by having both observers write to the same channel or by creating a third channel that collects the other two.

The is no function to check whether a stream is in progress. But since you are using coroutines it should be easy to write your own.

Was my information helpful? Did you manage to resolve your issue?

Closing, please do not hesitate to create a new issue if you face any more problems.