Ubuntu22.04 - brpc的安装和使用

news/2025/2/24 17:52:54

目录

  • 介绍
  • 安装
  • 使用

介绍

brpc 是用 c++语言编写的工业级 RPC 框架,常用于搜索、存储、机器学习、广告、推荐等高性能系统

安装

先安装依赖
apt-get install -y git g++ make libssl-dev libprotobuf-dev libprotoc-dev protobuf-compiler libleveldb-dev libgflags-dev
安装brpc
去github上下载https://github.com/apache/brpc.git
在这里插入图片描述
依次执行
unzip brpc-master.zip
cd brpc-master
mkdir build && cd build
cmake -DCMAKE_INSTALL_PREFIX=/usr .. && cmake --build . -j6
make && sudo make install

使用

示例:
main.proto文件

syntax="proto3";

package example;

option cc_generic_services = true;  // 这个选项的功能其实就是 生成框架代码的时候, 内部包含了rpc相关接口的内容

message EchoRequest{
    string message = 1;
}

message EchoResponse{
    string message = 1;
}

//这是回显服务器的名称
service EchoService{
    // EchoRequest参数      EchoResponse返回类型
    rpc Echo(EchoRequest) returns (EchoResponse);   // 定义rpc接口
}

client.cc文件

#include <brpc/channel.h>
#include <thread>
#include "main.pb.h"

//brpc是同步调用还是异步调用, 是客户端来决定的  -- 明天ai问一下

void callback(brpc::Controller* cntl, ::example::EchoResponse* response){
    std::unique_ptr<brpc::Controller> cntl_guard(cntl);
    std::unique_ptr<example::EchoResponse> resp_guard(response);
    if (cntl->Failed() == true) {
        std::cout << "Rpc调用失败: " << cntl->ErrorText() << std::endl;
        return;
    }
    std::cout << "收到响应: " << response->message() << std::endl;
}

int main(int argc, char* argv[])
{
    //1. 构造Channel信道, 连接服务器
    brpc::ChannelOptions options;
    options.connect_timeout_ms = -1;    //连接等待超时时间, -1表示一直等待
    options.timeout_ms = -1;        //rpc请求等待超时时间, -1表示一直等待
    options.protocol = "baidu_std"; //序列化协议, 默认使用baidu_std
    brpc::Channel channel;  //为什么要有这个类? 没有这个类就不能进行通信, 理解为管道 
    int ret = channel.Init("127.0.0.1:8080", &options); //参数1: 服务器地址  参数2: 客户端连接时的配置
    if (ret == -1) {
        std::cout << "初始化信道失败! \n";
        return -1;
    }

    //2. 构造EchoService_Stub对象, 用于进行rpc调用
    example::EchoService_Stub stub(&channel);   //相当于客户端类
    //3. 进行Rpc调用
    example::EchoRequest req;
    req.set_message("你好~比特~!");


    //这个Controller提供了很多功能, 其中一个就是辨别返回值的成功或失败
    brpc::Controller* cntl = new brpc::Controller();
    //如果我们不想同步处理, 即不想等待响应, 希望异步, 就要通过Controller设置回调函数
    //注意一个问题: 可能在处理回调函数的时候,如果这个cntl和rsp是栈对象 这个cntl,rsp会被释放掉, 如果这个main函数
    //是一个普通的函数,则处理这个回调函数的时候,可能这个函数已经结束了, 这个cntl,rsp已经被释放掉了,这就可能出现错误

    example::EchoResponse* rsp = new example::EchoResponse();  //用于接收返回值的
    auto clusure = google::protobuf::NewCallback(callback, cntl, rsp);
    stub.Echo(cntl, &req, rsp, clusure);    //异步调用
    // stub.Echo(cntl, &req, rsp, nullptr);      //最后一个参数, 如果是异步调用, 则要传参让服务器设置去run, 我们是同步调用, 所以就不用设置了
    // if(cntl->Failed() == true) {
    //     std::cout << "Rpc调用失败: " << cntl->ErrorText() << std::endl;
    //     return -1;
    // }
    // std::cout << "收到响应: " << rsp->message() << std::endl;

    std::this_thread::sleep_for(std::chrono::seconds(3));
    return 0;   //如果是异步调用, 主函数需要等待, 否则程序可能会直接结束
}

server.cc文件

#include <brpc/server.h>
#include <butil/logging.h>
#include "main.pb.h"

//1. 继承与EchoService创建一个子类, 并实现rpc调用的业务功能
class EchoServiceImpl : public example::EchoService{     //EchoService类是远程调用rpc服务的类 - 就是真正进行sum计算的
    public:
    // 重写这个虚函数
    //RpcController: 返回结果是成功或失败   
    //request客户端的请求   response服务器要构造的响应
    //Closure: 大格局理解 服务端是异步执行的, 将Response的响应设置完了, 再调用run函数, 告诉服务器可以发给客户端响应了
    void Echo(google::protobuf::RpcController* controller, const ::example::EchoRequest* request,
              ::example::EchoResponse* response, ::google::protobuf::Closure* done) //至于这个函数是在业务服务器 主线程还是线程池中执行, 我们并不关心
    {
        //防止程序员忘记最后调用run函数, 所以用智能指针来管理起来
        brpc::ClosureGuard rpc_guard(done);
        std::cout << "收到消息:" << request->message() << std::endl;

        std::string str = request->message() + "--这是响应!!";
        response->set_message(str);
        // done->Run()      如果不写上面的guard, 则需要加上这句话
    }
};

int main(int argc, char* argv[])
{
    // 关闭brpc的默认日志输出
    logging::LoggingSettings settings;
    settings.logging_dest = logging::LoggingDestination::LOG_TO_NONE;
    logging::InitLogging(settings);
    //2. 构造服务器对象
    brpc::Server server;
    
    //3. 向服务器对象中, 新增EchoService服务
    EchoServiceImpl echo_service;
    int ret = server.AddService(&echo_service, brpc::ServiceOwnership::SERVER_DOESNT_OWN_SERVICE);
    if (ret == -1){
        std::cout << "添加Rpc服务失败!\n";
        return -1;
    }
    //参数1: 添加服务, 只有你添加了服务, 服务器才能处理你对应的请求, 和路由很像    类型为Service*, EchoServiceImpl是它的子类
    //参数2: 添加服务失败的时候, 服务器是否会删除该对象  因为echo_service是局部变量, 所以不用去释放

    //4. 启动服务器
    brpc::ServerOptions options;    //启动服务器时的配置类
    options.idle_timeout_sec = -1;  //连接空闲超时时间 - 超时后连接被关闭
    options.num_threads = 1;        //io线程数量
    ret = server.Start(8080, &options);
    if (ret == -1) {
        std::cout << "启动服务器失败! \n";
        return -1;
    }
    server.RunUntilAskedToQuit();   //服务器一直循环运行
    return 0;
}

先用protoc进行编译:
在这里插入图片描述
编译运行:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述


http://www.niftyadmin.cn/n/5864675.html

相关文章

51单片机-串口通信编程

串行口工作之前&#xff0c;应对其进行初始化&#xff0c;主要是设置产生波特率的定时器1、串行口控制盒中断控制。具体步骤如下&#xff1a; 确定T1的工作方式&#xff08;编程TMOD寄存器&#xff09;计算T1的初值&#xff0c;装载TH1\TL1启动T1&#xff08;编程TCON中的TR1位…

CentOS 下安装和配置 HTTPD 服务的详细指南

CentOS 下安装和配置 HTTPD 服务的详细指南 CentOS 下安装和配置 HTTPD 服务的详细指南1. 环境准备2. 安装 HTTPD 服务2.1 更新系统2.2 安装 HTTPD2.3 启动 HTTPD 服务2.4 检查 HTTPD 服务状态 3. 配置防火墙3.1 开放 HTTP 和 HTTPS 端口3.2 验证防火墙规则 4. 配置 HTTPD4.1 主…

项目实战--网页五子棋(匹配模块)(4)

上期我们完成了游戏大厅的前端部分内容&#xff0c;今天我们实现后端部分内容 1. 维护在线用户 在用户登录成功后&#xff0c;我们可以维护好用户的websocket会话&#xff0c;把用户表示为在线状态&#xff0c;方便获取到用户的websocket会话 package org.ting.j20250110_g…

【Java 面试 八股文】JVM 虚拟机篇

JVM 虚拟机篇 1. JVM组成1.1 JVM由那些部分组成&#xff0c;运行流程是什么&#xff1f;1.2 什么是程序计数器&#xff1f;1.3 你能给我详细的介绍Java堆吗?1.4 Java 虚拟机栈1.4.1 Java Virtual machine Stacks (java 虚拟机栈)1.4.2 栈和堆的区别1.4.3 垃圾回收是否涉及栈内…

2024华为OD机试真题-水仙花数Ⅰ(C++)-E卷B卷-100分

2024华为OD机试最新题库-(C卷+D卷+E卷)-(JAVA、Python、C++) 目录 题目描述 输入描述 输出描述 用例1 用例2 解题思路 考点 代码 c++ 题目描述 所谓水仙花数,是指一个n位的正整数,其各位数字的n次方和等于该数本身。 例如153是水仙花数,153是一个3位数,并且153…

uni-app 系统学习,从入门到实战(一)—— 从零开始搭建第一个跨平台应用

全篇大概 1500 字&#xff0c;建议阅读时间 5min 简介 UniApp 是一个基于 Vue.js 的跨平台开发框架&#xff0c;开发者可以通过编写一套代码&#xff0c;同时发布到 iOS、Android、H5、微信小程序、支付宝小程序、百度小程序等多个平台。本文将带你从零开始&#xff0…

Docker内存芭蕾:优雅调整容器内存的极限艺术

title: “&#x1f4be; Docker内存芭蕾&#xff1a;优雅调整容器内存的极限艺术” author: “Cjs” date: “2025-2-23” emoji: “&#x1fa70;&#x1f4a5;&#x1f4ca;” 当你的容器变成内存吸血鬼时… &#x1f680; 完美内存编排示范 &#x1f4dc; 智能内存管家脚本…

c语言 枚举用法技巧

c语言 枚举用法技巧 typedef enum {Red 0,Green } sc4336p_res_mode;int i 0; td_u8 image_mode;image_mode (sc4336p_res_mode)i; 此分析摘自chatgpt 在你提供的 C 代码片段中&#xff0c;你尝试将一个整数值 i 转换为 sc4336p_res_mode 枚举类型&#xff0c;并将其赋值给…