Julian Gold
Julian Gold

Reputation: 1286

How to know if a GRPC server is available

If a gRPC client starts before the server, it exits with an exception. The application I am working on starts a bunch of servers and clients (near) simultaneously, however, and I have to be robust with respect to execution order. If the client starts before the server, I want it to wait until the server shows up.

I modified the HelloWorld python client example as follows:

done = False
while not done:
    try:
        response = stub.SayHello(helloworld_pb2.HelloRequest(name='you'), timeout=1)
        print("Greeter client received: " + response.message)
        done = True
    except:
        print('Waiting for server connect...')
        time.sleep(1)

so now if I start the client before the server, I get the 'Waiting for server connect...' message scrolling up my terminal window as expected. Then I start the server, and it connects... eventually. In fact it takes about ten seconds before the 'Hello you' messages appears, which is surprisingly long. Why might it be so slow, and is there a robust way to check for server connection?

Upvotes: 5

Views: 18417

Answers (3)

sman591
sman591

Reputation: 560

I believe what you are looking for is Wait-for-Ready semantics.

As of 2018, this is built-in for Python via the wait_for_ready flag. The grpc GitHub source has a few examples: https://github.com/grpc/grpc/tree/master/examples/python/wait_for_ready

Translating your question directly, you'd want something like this:

response = stub.SayHello(
    helloworld_pb2.HelloRequest(name='you'), 
    timeout=1,
    wait_for_ready=True
)
print("Greeter client received: " + response.message)

wait_for_ready was introduced for Python in 2018, version 1.17.0, and graduated from "experimental" state in 2023 with version 1.53.0

Upvotes: 2

techkuz
techkuz

Reputation: 3956

import grpc

TIMEOUT_SEC = 15
def grpc_server_on(channel) -> bool:
    try:
        grpc.channel_ready_future(channel).result(timeout=TIMEOUT_SEC)
        return True
    except grpc.FutureTimeoutError:
        return False

The channel_ready_future function allows the client to wait for a specified timeout duration (in seconds) for the server to be ready. If our client times out, it raises.

Upvotes: 9

Trevor V
Trevor V

Reputation: 2131

Take a look at ChannelConnectivity - I am a go programmer but it should be the same in python. What I do is create while/for loop and when the "ChannelConnectivity" is set to "READY" I create the client from the connection and then continue.

Upvotes: 5

Related Questions