gRPC用python尝鲜

0 准备

参考资料

官方文档

下载gRPC

git clone -b v1.27.0 https://github.com/grpc/grpc

python环境

python virtualenv环境准备

$ python -m pip install virtualenv
$ virtualenv grpc_venv
$ source grpc_venv/Scripts/activate
$ python -m pip install --upgrade pip

在环境中添加如下两个包:

pip install grpcio
pip install grpcio-tools

或者可以全局环境添加

$ sudo python -m pip install grpcio
$ sudo python -m pip install grpcio-tools

或者直接在ide里面添加。
在这里插入图片描述

1 编辑.proto文件

文件路径:grpc/examples/protos/route_guide.proto

2. 根据.proto文件生成服务器端和客户端代码

cd grpc/examples/python/route_guide
python -m grpc_tools.protoc -I../../protos --python_out=. --grpc_python_out=. ../../protos/route_guide.proto

这个命令产生如下两个文件:
test_grpc\grpc\examples\python\route_guide\route_guide_pb2_grpc.py
test_grpc\grpc\examples\python\route_guide\route_guide_pb2.py

创建服务器端处理程序

route_guide_server.py

服务器端代码分析

实现RouteGuide

简单RPC代码
def GetFeature(self, request, context):
  feature = get_feature(self.db, request)
  if feature is None:
    return route_guide_pb2.Feature(name="", location=request)
  else:
    return feature
返回流式RPC代码
def ListFeatures(self, request, context):
  left = min(request.lo.longitude, request.hi.longitude)
  right = max(request.lo.longitude, request.hi.longitude)
  top = max(request.lo.latitude, request.hi.latitude)
  bottom = min(request.lo.latitude, request.hi.latitude)
  for feature in self.db:
    if (feature.location.longitude >= left and
        feature.location.longitude <= right and
        feature.location.latitude >= bottom and
        feature.location.latitude <= top):
      yield feature
请求流式RPC代码
def RecordRoute(self, request_iterator, context):
  point_count = 0
  feature_count = 0
  distance = 0.0
  prev_point = None

  start_time = time.time()
  for point in request_iterator:
    point_count += 1
    if get_feature(self.db, point):
      feature_count += 1
    if prev_point:
      distance += get_distance(prev_point, point)
    prev_point = point

  elapsed_time = time.time() - start_time
  return route_guide_pb2.RouteSummary(point_count=point_count,
                                      feature_count=feature_count,
                                      distance=int(distance),
                                      elapsed_time=int(elapsed_time))
双向流式RPC代码
def RouteChat(self, request_iterator, context):
  prev_notes = []
  for new_note in request_iterator:
    for prev_note in prev_notes:
      if prev_note.location == new_note.location:
        yield prev_note
    prev_notes.append(new_note)

启动服务器代码

def serve():
  server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
  route_guide_pb2_grpc.add_RouteGuideServicer_to_server(
      RouteGuideServicer(), server)
  server.add_insecure_port('[::]:50051')
  server.start()

创建客户端

route_guide_client.py

客户端代码分析

创建stub

channel = grpc.insecure_channel('localhost:50051')
stub = route_guide_pb2_grpc.RouteGuideStub(channel)

调用服务器方法

对于返回单个响应的RPC方法(“响应一元”方法),gRPC Python支持同步(阻塞)和异步(非阻塞)控制流语义。 对于响应流式RPC方法,调用立即返回响应值的迭代器。 调用该迭代器的next()方法块,直到要从该迭代器产生的响应变为可用为止。

调用简单RPC代码

对简单RPC GetFeature的同步调用几乎与调用本地方法一样简单。 RPC调用等待服务器响应,并且将返回响应或引发异常:

feature = stub.GetFeature(point)

对GetFeature的异步调用与此类似,但是就像在线程池中异步调用本地方法一样:

feature_future = stub.GetFeature.future(point)
feature = feature_future.result()
调用响应流式RPC
for feature in stub.ListFeatures(rectangle):
调用请求流式RPC

调用请求流RecordRoute类似于将迭代器传递给本地方法。就像上面的简单RPC也返回单个响应一样,可以同步或异步调用它:

route_summary = stub.RecordRoute(point_iterator)
route_summary_future = stub.RecordRoute.future(point_iterator)
route_summary = route_summary_future.result()
调用双向流式RPC

调用双向流RouteChat具有服务流和响应流语义的组合(在服务端就是这种情况):

for received_route_note in stub.RouteChat(sent_route_note_iterator):
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值