1.  gRPC简述

RPC,远程方法调用,就是像调用本地方法一样调用远程方法。

gRPC是Google实现的一种RPC框架,基于HTTP/2标准设计,带来诸如双向流、流控、头部压缩、单 TCP 连接上的多复用请求等特。这些特性使得其在移动设备上表现更好,更省电和节省空间占用。目前提供 C、Java 和 Go 语言版本,分别是:grpc, grpc-java, grpc-go. 其中 C 版本支持 C, C++, Node.js, Python, Ruby, Objective-C, PHP 和 C# 支持。

基本原理:在服务端提供方法,并运行服务器监听客户端请求;客户端调用RPC方法,gRPC客户端向服务端发送请求,并将结果返回给客户端调用函数。

gRPC 默认使用 protocol buffers,这是 Google 开源的一套成熟的结构数据序列化机制(当然也可以使用其他数据格式如 JSON)。推荐使用protobuf v3。

RPC框架要做到的最基本的三件事:

1)服务端如何确定客户端要调用的函数;

在远程调用中,客户端和服务端分别维护一个【ID->函数】的对应表, ID在所有进程中都是唯一确定的。客户端在做远程过程调用时,附上这个ID,服务端通过查表,来确定客户端需要调用的函数,然后执行相应函数的代码。

2)如何进行序列化和反序列化;

客户端和服务端交互时将参数或结果转化为字节流在网络中传输,那么数据转化为字节流的或者将字节流转换成能读取的固定格式时就需要进行序列化和反序列化,序列化和反序列化的速度也会影响远程调用的效率。

3)如何进行网络传输(选择何种网络协议);

多数RPC框架选择TCP作为传输协议,也有部分选择HTTP。如gRPC使用HTTP2。不同的协议各有利弊。TCP更加高效,而HTTP在实际应用中更加的灵活。

REST与RPC应用场景

REST和RPC都常用于微服务架构中。

1)HTTP相对更规范,更标准,更通用,无论哪种语言都支持http协议。如果你是对外开放API,例如开放平台,外部的编程语言多种多样,你无法拒绝对每种语言的支持,现在开源中间件,基本最先支持的几个协议都包含RESTful。

2)RPC 框架作为架构微服务化的基础组件,它能大大降低架构微服务化的成本,提高调用方与服务提供方的研发效率,屏蔽跨进程调用函数(服务)的各类复杂细节。让调用方感觉就像调用本地函数一样调用远端函数、让服务提供方感觉就像实现一个本地函数一样来实现服务。

REST调用及测试都很方便,RPC就显得有点繁琐,但是RPC的效率是毋庸置疑的,所以建议在多系统之间的内部调用采用RPC。对外提供的服务,Rest更加合适。

2.  安装

$ git clone https://github.com/grpc/grpc.git

$ cd grpc

$ git submodule update--init

$make

$sudo make install

注:执行submodule时时间较长

[INSTALL] Installing publicC headers

[MAKE] Generating cache.mk

[STRIP] Stripping libaddress_sorting.a

[STRIP] Stripping libgpr.a

[STRIP] Stripping libgrpc.a

[STRIP] Stripping libgrpc_cronet.a

[STRIP] Stripping libgrpc_unsecure.a

[INSTALL] Installing C pkg-config files

[INSTALL] Installing libaddress_sorting.a

[INSTALL] Installing libgpr.a

[INSTALL] Installing libgrpc.a

[INSTALL] Installing libgrpc_cronet.a

[INSTALL] Installing libgrpc_unsecure.a

[STRIP] Stripping libaddress_sorting.so.7.0.0[STRIP] Stripping libgpr.so.7.0.0[STRIP] Stripping libgrpc.so.7.0.0[STRIP] Stripping libgrpc_cronet.so.7.0.0[STRIP] Stripping libgrpc_unsecure.so.7.0.0[INSTALL] Installing libaddress_sorting.so.7.0.0[INSTALL] Installing libgpr.so.7.0.0[INSTALL] Installing libgrpc.so.7.0.0[INSTALL] Installing libgrpc_cronet.so.7.0.0[INSTALL] Installing libgrpc_unsecure.so.7.0.0[INSTALL] Installingpublic C++headers

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc_plugin_support.a

[HOSTCXX] Compiling src/compiler/cpp_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_cpp_plugin

[HOSTCXX] Compiling src/compiler/csharp_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_csharp_plugin

[HOSTCXX] Compiling src/compiler/node_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_node_plugin

[HOSTCXX] Compiling src/compiler/objective_c_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_objective_c_plugin

[HOSTCXX] Compiling src/compiler/php_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_php_plugin

[HOSTCXX] Compiling src/compiler/python_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_python_plugin

[HOSTCXX] Compiling src/compiler/ruby_plugin.cc

[HOSTLD] Linking/home/wang/repo/grpc/bins/opt/grpc_ruby_plugin

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/channelz/channelz.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/channelz/channelz.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/health/v1/health.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/health/v1/health.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/echo_messages.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/echo_messages.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/simple_messages.proto

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/testing/echo.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/simple_messages.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/echo.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/duplicate/echo_duplicate.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/duplicate/echo_duplicate.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/core/stats.proto

[CXX] Compiling/home/wang/repo/grpc/gens/src/proto/grpc/core/stats.pb.cc

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/core/stats.proto

[CXX] Compiling /home/wang/repo/grpc/gens/src/proto/grpc/core/stats.grpc.pb.cc

[CXX] Compiling src/cpp/util/core_stats.cc

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc++_core_stats.a

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/testing/payloads.proto

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/testing/stats.proto

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/testing/control.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/payloads.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/stats.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/control.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/messages.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/messages.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/benchmark_service.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/benchmark_service.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/report_qps_scenario_service.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/report_qps_scenario_service.proto

[PROTOC] Generating protobuf CC file from src/proto/grpc/testing/worker_service.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/testing/worker_service.proto

[CXX] Compiling src/cpp/codegen/codegen_init.cc

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc++.a

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc++_cronet.a

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/status/status.proto

[CXX] Compiling/home/wang/repo/grpc/gens/src/proto/grpc/status/status.pb.cc

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/status/status.proto

[CXX] Compiling /home/wang/repo/grpc/gens/src/proto/grpc/status/status.grpc.pb.cc

[CXX] Compiling src/cpp/util/error_details.cc

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc++_error_details.a

[PROTOC] Generating protobuf CC filefrom src/proto/grpc/reflection/v1alpha/reflection.proto

[GRPC] Generating gRPC's protobuf service CC file from src/proto/grpc/reflection/v1alpha/reflection.proto

[CXX] Compiling src/cpp/ext/proto_server_reflection.cc

[CXX] Compiling src/cpp/ext/proto_server_reflection_plugin.cc

[CXX] Compiling/home/wang/repo/grpc/gens/src/proto/grpc/reflection/v1alpha/reflection.pb.cc

[CXX] Compiling/home/wang/repo/grpc/gens/src/proto/grpc/reflection/v1alpha/reflection.grpc.pb.cc

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc++_reflection.a

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpc++_unsecure.a

[CXX] Compiling src/cpp/server/channelz/channelz_service.cc

[CXX] Compiling src/cpp/server/channelz/channelz_service_plugin.cc

[CXX] Compiling/home/wang/repo/grpc/gens/src/proto/grpc/channelz/channelz.pb.cc

[CXX] Compiling/home/wang/repo/grpc/gens/src/proto/grpc/channelz/channelz.grpc.pb.cc

[AR] Creating/home/wang/repo/grpc/libs/opt/libgrpcpp_channelz.a

[STRIP] Stripping libgrpc++.a

[STRIP] Stripping libgrpc++_cronet.a

[STRIP] Stripping libgrpc++_error_details.a

[STRIP] Stripping libgrpc++_reflection.a

[STRIP] Stripping libgrpc++_unsecure.a

[STRIP] Stripping libgrpcpp_channelz.a

[INSTALL] Installing C++ pkg-config files

[INSTALL] Installing libgrpc++.a

[INSTALL] Installing libgrpc++_cronet.a

[INSTALL] Installing libgrpc++_error_details.a

[INSTALL] Installing libgrpc++_reflection.a

[INSTALL] Installing libgrpc++_unsecure.a

[INSTALL] Installing libgrpcpp_channelz.a

[LD] Linking/home/wang/repo/grpc/libs/opt/libgrpc++.so.1.20.0[LD] Linking/home/wang/repo/grpc/libs/opt/libgrpc++_cronet.so.1.20.0[LD] Linking/home/wang/repo/grpc/libs/opt/libgrpc++_error_details.so.1.20.0[LD] Linking/home/wang/repo/grpc/libs/opt/libgrpc++_reflection.so.1.20.0[LD] Linking/home/wang/repo/grpc/libs/opt/libgrpc++_unsecure.so.1.20.0[LD] Linking/home/wang/repo/grpc/libs/opt/libgrpcpp_channelz.so.1.20.0[STRIP] Stripping libgrpc++.so.1.20.0[STRIP] Stripping libgrpc++_cronet.so.1.20.0[STRIP] Stripping libgrpc++_error_details.so.1.20.0[STRIP] Stripping libgrpc++_reflection.so.1.20.0[STRIP] Stripping libgrpc++_unsecure.so.1.20.0[STRIP] Stripping libgrpcpp_channelz.so.1.20.0[INSTALL] Installing libgrpc++.so.1.20.0[INSTALL] Installing libgrpc++_cronet.so.1.20.0[INSTALL] Installing libgrpc++_error_details.so.1.20.0[INSTALL] Installing libgrpc++_reflection.so.1.20.0[INSTALL] Installing libgrpc++_unsecure.so.1.20.0[INSTALL] Installing libgrpcpp_channelz.so.1.20.0[INSTALL] Installing grpc protoc plugins

[INSTALL] Installing root certificates

install log

安装的文件包含:bin,include,lib,share(根证书)。

3.  应用

examples下有各语言版本的示例,examples/protoc是protoc示例文件。

如下演示的是helloworld示例,examples中不仅支持同步调用,还支持异步调用。

1. proto文件定义RPC方法及参数

helloworld.proto

syntax = "proto3";

option java_package= "io.grpc.examples";

package helloworld;//The greeter service definition.

service Greeter {//Sends a greeting

rpc SayHello (HelloRequest) returns (HelloReply) {}

}//The request message containing the user's name.

message HelloRequest {string name = 1;

}//The response message containing the greetings

message HelloReply {string message = 1;

}

编译生成c++源文件(grpc和应用)

protoc --grpc_out=. --plugin=protoc-gen-grpc=`which grpc_cpp_plugin` helloworld.proto

protoc--cpp_out=. helloworld.proto

2. server端代码

#include #include#include#include#ifdef BAZEL_BUILD

#include"examples/protos/helloworld.grpc.pb.h"

#else#include"helloworld.grpc.pb.h"

#endif

usinggrpc::Server;usinggrpc::ServerBuilder;usinggrpc::ServerContext;usinggrpc::Status;usinghelloworld::HelloRequest;usinghelloworld::HelloReply;usinghelloworld::Greeter;//Logic and data behind the server's behavior.

class GreeterServiceImpl final : publicGreeter::Service {

Status SayHello(ServerContext* context, const HelloRequest*request,

HelloReply* reply) override{

std::string prefix("Hello");

reply->set_message(prefix + request->name());returnStatus::OK;

}

};voidRunServer() {

std::string server_address("0.0.0.0:50051");

GreeterServiceImpl service;

ServerBuilder builder;//Listen on the given address without any authentication mechanism.

builder.AddListeningPort(server_address, grpc::InsecureServerCredentials());//Register "service" as the instance through which we'll communicate with//clients. In this case it corresponds to an *synchronous* service.

builder.RegisterService(&service);//Finally assemble the server.

std::unique_ptrserver(builder.BuildAndStart());

std::cout<< "Server listening on" << server_address <<:endl for the server to shutdown. note that some other thread must be shutting down this call ever return.>

server->Wait();

}int main(int argc, char**argv) {

RunServer();return 0;

}

编译执行:

g++ -o server helloworld.pb.cc helloworld.grpc.pb.cc server.cc -L/usr/local/lib `pkg-config --cflags protobuf grpc` -std=c++11 `pkg-config --libs protobuf grpc++ grpc` -Wl,--no-as-needed -lgrpc++_reflection -Wl,--as-needed -ldl

$ ./server

Server listening on0.0.0.0:50051

3.client端代码

#include #include#include#include#ifdef BAZEL_BUILD

#include"examples/protos/helloworld.grpc.pb.h"

#else#include"helloworld.grpc.pb.h"

#endif

usinggrpc::Channel;usinggrpc::ClientContext;usinggrpc::Status;usinghelloworld::HelloRequest;usinghelloworld::HelloReply;usinghelloworld::Greeter;classGreeterClient {public:

GreeterClient(std::shared_ptrchannel)

: stub_(Greeter::NewStub(channel)) {}//Assembles the client's payload, sends it and presents the response back//from the server.

std::string SayHello(const std::string&user) {//Data we are sending to the server.

HelloRequest request;

request.set_name(user);//Container for the data we expect from the server.

HelloReply reply;//Context for the client. It could be used to convey extra information to//the server and/or tweak certain RPC behaviors.

ClientContext context;//The actual RPC.

Status status = stub_->SayHello(&context, request, &reply);//Act upon its status.

if(status.ok()) {returnreply.message();

}else{

std::cout<< status.error_code() << ":" <

}

}private:

std::unique_ptr<:stub>stub_;

};int main(int argc, char**argv) {//Instantiate the client. It requires a channel, out of which the actual RPCs//are created. This channel models a connection to an endpoint (in this case,//localhost at port 50051). We indicate that the channel isn't authenticated//(use of InsecureChannelCredentials()).

GreeterClient greeter(grpc::CreateChannel("127.0.0.1:50051", grpc::InsecureChannelCredentials()));

std::string user("world");

std::string reply =greeter.SayHello(user);

std::cout<< "Greeter received:" << reply <<:endl>

}

编译执行:

g++ -o client helloworld.pb.cc helloworld.grpc.pb.cc client.cc -L/usr/local/lib `pkg-config --cflags protobuf grpc` -std=c++11 `pkg-config --libs protobuf grpc++ grpc` -Wl,--no-as-needed -lgrpc++_reflection -Wl,--as-needed -ldl

$ ./client

Greeter received: Hello world

参考:

8. gRPC(HTTP / 2)比使用HTTP / 2的REST更快吗?  默认情况下,gRPC不比HTTP / REST更快,但它为您提供了更快的工具。有些事情对于REST来说很难或不可能做到。

c++客户端 grpc_gRPC应用C++相关推荐

  1. springboot实现SSE服务端主动向客户端推送数据,java服务端向客户端推送数据,kotlin模拟客户端向服务端推送数据

    SSE服务端推送 服务器向浏览器推送信息,除了 WebSocket,还有一种方法:Server-Sent Events(以下简称 SSE).本文介绍它的用法. 在很多业务场景中,会涉及到服务端向客户端 ...

  2. Redis 笔记(16)— info 指令和命令行工具(查看内存、状态、客户端连接数、监控服务器、扫描大key、采样服务器、执行批量命令等)

    Info 命令返回关于 Redis 服务器的各种信息和统计数值.通过给定可选的参数 section ,可以让命令只返回某一部分的信息. 1. 显示模块 server : 一般 Redis 服务器信息, ...

  3. Redis 笔记(15)— 管道 pipeline(客户端将批量命令打包发送用来节省网络开销)

    Redis 是一种基于客户端-服务端模型以及请求/响应协议的 TCP 服务.这意味着通常情况下一个请求会遵循以下步骤: 客户端向服务端发送一个查询请求,并监听 Socket 返回,通常是以阻塞模式,等 ...

  4. Ubuntu NFS 服务器和客户端挂载详解

    1. NFS 基本介绍 1.1 NFS 简介 NFS 是 Network File System 的缩写,即网络文件系统.一种使用于分散式文件系统的协定,由 Sun 公司开发,于1984年向外公布.功 ...

  5. RPC 笔记(03)— gRPC 概念、安装、编译、客户端和服务端示例

    1. gRPC 概念 gRPC 是 Google 开源的一款高性能的 RPC 框架.GitHub 上介绍如下: gRPC is a modern, open source, high-performa ...

  6. etcd 笔记(06)— Client 结构定义、客户端(初始化、KV存储Get、Put、事务 Txn、压缩 Compact、Watch、Lease

    1. Client 定义 Client 定义如下: type Client struct {ClusterKVLeaseWatcherAuthMaintenance// 认证的用户名Username ...

  7. etcd 笔记(03)— etcd 客户端使用(键值的增、删、改、查)、watch监测键、lease使用(创建租约、撤销租约、刷新租期、查询租期)

    1. etcd 客户端 etcdctl 是一个命令行客户端,便于我们进行服务测试或手动修改数据库内容,etcdctl 在两个不同的 etcd 版本(v2 和 v3)下的功能和使用方式也完全不同. 一般 ...

  8. Go 学习笔记(76)— Go 标准库 net/http 创建客户端(发送 GET、POST 请求)

    1. Get 请求 1.1 使用 net/http 包的快捷方法 GET package mainimport ("fmt""io/ioutil""n ...

  9. Go 学习笔记(58)— Go 第三方库之 etcd/clientv3(连接客户端、PUT、GET、Lease、Op、Txn、Watch 基础概念说明)

    1. 安装 Golang 的 Etcd 包 我们使用 v3 版本的 etcd client , 首先通过 go get 下载并编译安装 etcd clinet v3. go get -v github ...

最新文章

  1. 多组两两比较用什么检验方法_用SPSS进行不同变量多组间两两比较卡方检验.pdf...
  2. 听说你想去大厂看学姐,带你看看拼多多运营面经
  3. pe文件被装入内存时按64k对齐
  4. java实现套接字网络编程_Java网络编程(一)Socket套接字
  5. Android Binder机制(1501210451 张志康)
  6. Linux输入密码接口,Linux下搭建接口自动化测试平台
  7. 分组背包(信息学奥赛一本通-T1272)
  8. Centos npm 安装JDK及配置环境变量
  9. Trains 归纳法
  10. Shell获取多行输入并输出每行的第3个字符
  11. 使用npm安装vue项目+使用
  12. c++调用powershell_告别 Windows 终端的难看难用,从改造 PowerShell 的外观开始
  13. selenium下载图片
  14. mfs网络分布式文件系统、高可用、iscsi存储方式的mfs、fence
  15. 美标/国标耳机接口区别
  16. 福利!在线编写代码的网站
  17. 为什么RocketMQ是金融核心系统消息中间件的第一选择
  18. 探岳车型编码_探岳这个车有钥匙编码吗?
  19. 【async-excel】一款异步导入导出excel的组件
  20. DFIG_Wind_Turbine:基于MATLAB/Simulink的双馈异步风力发电机仿真模型,控制方案采用矢量控制,电机的有功功率和无功功率由转子侧变换器控制

热门文章

  1. 浏览器攻击框架BeEF Part 5:攻击Web应用与攻击网络
  2. 追忆我的2008-爱上读书篇
  3. uniapp:Google开发者证书信息有误,请重新填写相关信息 Android 证书文件不是有效的keystore文件Hbulider
  4. ADF4002【分频器】(康威)
  5. LS1043A lsdk2108 调试记录
  6. 共识机制9-(帕克索斯算法)
  7. 云呐|医疗医院固定资产设备管理如何高效管理
  8. Linux调整挂载磁盘分区大小
  9. 电脑便签怎么嵌入桌面使其不可移动呢?
  10. 拼多多买菜入驻永善县了,支持自提