--Create a simple gRPC process in Python. --Try to create a process that requests some value and returns the result like REST.
.proto
file and compile it.Install with pip
$ pip install grpcio-tools
simple.proto
syntax = "proto3";
package simple;
// request
message SimpleRequest{
string name = 1;
string msg = 2;
}
// response
message SimpleResponse{
string reply_msg = 1;
}
// interface
service SimpleService{
rpc SimpleSend (SimpleRequest) returns (SimpleResponse) {}
}
Create and execute the following source. (compile)
Simple_pb2.py
and simple_pb2_grpc.py
are created in the same folder.
codegen.py
from grpc.tools import protoc
protoc.main(
(
'',
'-I.',
'--python_out=.',
'--grpc_python_out=.',
'simple.proto',
)
)
Run
$ python codegen.py
Server side
server.py
import grpc
import time
import simple_pb2
import simple_pb2_grpc
from concurrent import futures
class SimpleServiceServicer(simple_pb2_grpc.SimpleServiceServicer):
def __init__(self):
pass
def SimpleSend(self, request, context):
print('logging: name {}, msg {}'.format(request.name, request.msg))
#Match with Response in proto file
return simple_pb2.SimpleResponse(
reply_msg = 'Hello! ' + request.name + '. Your message is ' + request.msg
)
# start server
server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
simple_pb2_grpc.add_SimpleServiceServicer_to_server(SimpleServiceServicer(), server)
server.add_insecure_port('[::]:5051')
server.start()
print('run server')
# wait
try:
while True:
time.sleep(3600)
except KeyboardInterrupt:
# stop server
server.stop(0)
--Source explanation
--Match the class name with service (SimpleServie) + Servicer in the proto file.
--Match the function name (SimpleSend) with rpc. Since it is a function name, snake case (simple_send) may be better for Python
--Since SimpleResponse
is defined in simple_pb2
, response is returned from there.
Client side
client.py
import grpc
import simple_pb2
import simple_pb2_grpc
with grpc.insecure_channel('localhost:5051') as channel:
stub = simple_pb2_grpc.SimpleServiceStub(channel)
name = "Tom"
msg = "Test"
response = stub.SimpleSend(simple_pb2.SimpleRequest(name=name, msg=msg))
print('Reply: ', response.reply_msg)
--Source explanation
--SimpleRequest
takes name and msg as arguments. Image that is passed to it and generates a class
--Calling the SimpleSend
function of the stub and passing the generated class as an argument to it
--Output reply_msg included in response
start server
$ python server.py
run server
Client execution
$ python client.py
Reply: Hello! Tom. Your message is Test
Process finished with exit code 0
C:\Users\grpc directory
2020/01/21 17:47 <DIR> .
2020/01/21 17:47 <DIR> ..
2020/01/21 17:45 327 client.py
2020/01/21 14:31 173 codegen.py
2020/01/21 17:47 851 server.py
2020/01/21 17:43 300 simple.proto
2020/01/21 17:43 4,212 simple_pb2.py
2020/01/21 17:43 1,342 simple_pb2_grpc.py
.proto file
syntax = "proto3";
package simple;
// request
message SimpleRequest{
}
// response
message SimpleResponse{
repeated string msgs = 1; //Use repeated
}
// interface
service SimpleService{
rpc simple_send (SimpleRequest) returns (SimpleResponse) {}
}
Server side
Server that returns a list
import grpc
import time
import simple_iter_pb2
import simple_iter_pb2_grpc
from concurrent import futures
class SimpleServiceServicer(simple_iter_pb2_grpc.SimpleServiceServicer):
def __init__(self):
pass
def simple_send(self, request, context):
sample_data = ['message1', 'message2']
return simple_iter_pb2.SimpleResponse(msgs=sample_data) #Don't forget the list name
# start server
server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
simple_iter_pb2_grpc.add_SimpleServiceServicer_to_server(SimpleServiceServicer(), server)
server.add_insecure_port('[::]:5051')
server.start()
print('run server')
# wait
try:
while True:
time.sleep(3600)
except KeyboardInterrupt:
# stop server
server.stop(0)
.proto file
syntax = "proto3";
package simple;
// request
message SimpleRequest{
}
// response
message SimpleResponse{
map<string, string> msg = 1; //use map
}
// interface
service SimpleService{
rpc simple_send (SimpleRequest) returns (SimpleResponse) {}
}
Server omitted
The following articles were very helpful. There is a more detailed description.
-Inter-application communication with gRPC and Protocol Buffers / Python -Try bidirectional communication with gRPC in Python. -Implement API with gRPC (Go)
Recommended Posts