brpc 从零到一的构建与部署实战指南:源码编译、依赖管理、测试与实例追踪
2026/9/21 16:39:52 网站建设 项目流程

brpc 从零到一的构建与部署实战指南:源码编译、依赖管理、测试与实例追踪

【免费下载链接】brpcbrpc is an Industrial-grade RPC framework using C++ Language, which is often used in high performance system such as Search, Storage, Machine learning, Advertisement, Recommendation etc. "brpc" means "better RPC".项目地址: https://gitcode.com/gh_mirrors/brpc6/brpc

本文以 Apache brpc 官方文档 docs/cn/getting_started.md 为核心骨架,结合当前仓库内的config_brpc.sh、CMakeLists.txt、example/echo_c++ 示例与 Dockerfile 等源码佐证,系统讲解 brpc 在 Ubuntu、CentOS、macOS、Docker 等环境下的依赖准备、config_brpc.sh与 CMake 两条编译路线、样例运行与单元测试方法,以及 tcmalloc、glog、thrift 等可选组件的链接注意事项。读完本文,你将从零完成 brpc 的编译安装,跑通第一个 echo 服务,并具备按需定制构建选项、排查链接异常的能力。

1. 构建总览:为什么 brpc 鼓励静态链接

brpc 的构建设计有一个核心理念:鼓励静态链接依赖。这样做的直接收益是,运行 brpc 服务的每台机器不再需要单独安装 gflags、protobuf、leveldb 等依赖库,二进制自带全部依赖,部署与迁移成本大幅降低。

brpc 的三项基础依赖及其用途如下:

依赖用途
gflags广泛用于定义全局选项(如端口、超时、负载均衡算法等)
protobuf消息序列化与 RPC 服务接口定义
leveldb 记录 RPC 调用,用于链路追踪

其中 leveldb 与 rpcz 的绑定关系可以在文档与源码中得到印证:rpcz 是 brpc 自带的 RPC 追踪模块,通过内置服务查看最近一段时间的 RPC 调用记录,其落盘存储依赖 leveldb。

从 CMakeLists.txt 可以看到,无论使用 CMake 还是config_brpc.sh,最终链接库集合都包含gflags、protobuf、leveldb、protoc、ssl、crypto、dl、z这一套基础依赖,这正对应了文档中声明的依赖清单。

2. 支持的环境总览

brpc 官方支持以下五类编译环境,本文后续小节将逐一给出完整步骤:

  • Ubuntu / LinuxMint / WSL(第 3 节)
  • Fedora / CentOS(第 4 节)
  • 自己构建依赖的 Linux(第 5 节)
  • macOS(第 6 节)
  • Docker(第 7 节)

需要特别说明的是,macOS 版本在相同硬件条件下性能可能明显低于 Linux 版本。如果你的服务对性能敏感,请勿将 macOS 作为生产环境。

3. Ubuntu/LinuxMint/WSL 编译指南

3.1 依赖准备

Debian 系发行版(Ubuntu、LinuxMint、WSL)使用 apt 安装全部基础依赖:

sudo apt-get install -y git g++ make libssl-dev libgflags-dev libprotobuf-dev libprotoc-dev protobuf-compiler libleveldb-dev

可选依赖按需安装:

  • 静态链接 leveldb 需要 snappy
sudo apt-get install -y libsnappy-dev
  • 通过源码编译生成 leveldb 静态库(当发行版不自带静态库时使用):
git clone --recurse-submodules https://github.com/google/leveldb.git mkdir -p build && cd build cmake -DCMAKE_BUILD_TYPE=Release -DCMAKE_POSITION_INDEPENDENT_CODE=ON .. && cmake --build . sudo cp -r ../include/leveldb /usr/include/ && sudo cp libleveldb.a /usr/lib/

注意:-DCMAKE_POSITION_INDEPENDENT_CODE=ON很关键,它让 leveldb 以 PIC(位置无关代码)方式编译,否则后续静态链接进 brpc 共享库或可执行文件时会报重定位错误。

  • 在样例中启用 cpu/heap profiler
sudo apt-get install -y libgoogle-perftools-dev
  • 运行单元测试需要 gtest(Debian 系默认不编译 gtest,需手动编译):
sudo apt-get install -y cmake libgtest-dev && cd /usr/src/gtest && sudo cmake . && sudo make && sudo mv lib/libgtest* /usr/lib/ && cd -

如果/usr/src/gtest不存在,请尝试/usr/src/googletest/googletest(不同 Ubuntu 版本源码目录位置有差异)。

3.2 使用 config_brpc.sh 编译 brpc

克隆 brpc 仓库并进入项目目录后,执行:

$ sh config_brpc.sh --headers=/usr/include --libs=/usr/lib $ make

脚本工作原理可以从 config_brpc.sh 的源码看出端倪:它用getopt解析参数,将--headers/--libs提供的路径转换成绝对路径(readlink -f/realpath),随后在指定路径中递归查找libgflagslibprotobuflibleveldblibssl等库文件,并自动探测 protobuf 版本、gflags 命名空间,最终生成config.mksrc/butil/config.h两个构建配置文件,make依据它们完成编译。值得一提的是,脚本会在--with-glog时向src/butil/config.h写入BRPC_WITH_GLOG宏,这一机制决定了 brpc 内部日志实现与 glog 的切换。

常用配置选项:

选项作用
--headers=PATH指定头文件搜索路径(可传多个,空格分隔)
--libs=PATH指定库文件搜索路径(可传多个,空格分隔)
--cc=clang --cxx=clang++切换编译器为 clang
--nodebugsymbols不链接调试符号,生成更轻量的二进制
--with-glog使用 glog 版日志
--with-thrift启用 thrift 支持

注意:从 config_brpc.sh 可以看到,--cc--cxx必须同时设置或同时不设置;在 Darwin 平台脚本默认使用 clang,其他平台默认使用 gcc/g++。

运行样例

$ cd example/echo_c++ $ make $ ./echo_server & $ ./echo_client

默认情况下样例链接 brpc 的静态库。如果你想链接 brpc 的共享库,请依次执行:make cleanLINK_SO=1 make。这一机制在 example/echo_c++/Makefile 中有明确实现:Linux 下默认用-Wl,-Bstatic $(STATIC_LINKINGS) -Wl,-Bdynamic静态链接 brpc 与依赖;当LINK_SO非空时改用-lbrpc动态链接。

运行测试

$ cd test $ make $ sh run_tests.sh

3.3 使用 cmake 编译 brpc

mkdir build && cd build && cmake .. && cmake --build . -j6

对于 cmake 3.13+,也可以使用如下更简洁的命令:

cmake -B build && cmake --build build -j6

CMake 路线的关键选项(均定义在 CMakeLists.txt 顶部):

CMake 选项默认值作用
-DWITH_GLOG=ONOFF使用 glog 日志
-DWITH_THRIFT=ONOFF启用 thrift framed 协议
-DWITH_DEBUG_SYMBOLS=OFFON关闭调试符号
-DWITH_RDMA=ONOFF启用 RDMA 支持
-DWITH_MESALINK=ONOFF使用 MesaLink(OpenSSL 替代实现)
-DWITH_BORINGSSL=ONOFF使用 BoringSSL
-DWITH_SNAPPY=ONOFF链接 snappy
-DBUILD_UNIT_TESTS=ONOFF构建单元测试
-DBUILD_BRPC_TOOLS=OFFON构建 brpc 工具集

其他实用技巧:

  • 要帮助 VSCode 或 Emacs(LSP)正确理解代码,添加-DCMAKE_EXPORT_COMPILE_COMMANDS=ON生成compile_commands.json
  • 要修改编译器为 clang,修改环境变量CCCXXclangclang++
  • 不想链接调试符号:先移除build/CMakeCache.txt,再用-DWITH_DEBUG_SYMBOLS=OFF重新执行 cmake。
  • 想让 brpc 使用 glog:用-DWITH_GLOG=ON执行 cmake。
  • 要启用 thrift 支持:先安装 thrift,再用-DWITH_THRIFT=ON执行 cmake。

用 cmake 运行样例

$ cd example/echo_c++ $ cmake -B build && cmake --build build -j4 $ ./echo_server & $ ./echo_client

上述操作默认链接 brpc 的静态库。若想链接共享库,先移除CMakeCache.txt,再用-DLINK_SO=ON重新执行 cmake(该选项定义于 example/echo_c++/CMakeLists.txt)。

运行测试

$ mkdir build && cd build && cmake -DBUILD_UNIT_TESTS=ON .. && make && make test

3.4 编译完成后的验证:echo 样例源码导读

config_brpc.sh与 CMake 两种路线殊途同归,最终产物落在output/liboutput/include目录。为了让你对"构建成功"有一个可验证的感性认识,这里简要解读 example/echo_c++ 的样例结构:

  • echo.proto:定义EchoRequest/EchoResponse消息与EchoService.Echo方法;
  • server.cpp:实现EchoServiceImpl,通过brpc::Server::AddService注册服务,server.Start启动监听(默认端口 8000,可用--port修改),RunUntilAskedToQuit等待 Ctrl-C;
  • client.cpp:创建brpc::Channelchannel.Init指向0.0.0.0:8000,构建EchoService_Stub后每 1 秒发送一次hello world请求,并打印响应与延迟。

运行./echo_server &后再运行./echo_client,客户端会输出类似Received response from ...: hello world ... latency=...us的日志,同时服务端打印收到请求的来源地址与内容,这就是构建成功最直接的验证。

4. Fedora/CentOS 编译指南

4.1 依赖准备

CentOS 一般需要先安装 EPEL 仓库,否则很多包默认不可用:

sudo yum install epel-release

安装依赖:

sudo yum install git gcc-c++ make openssl-devel gflags-devel protobuf-devel protobuf-compiler leveldb-devel

可选依赖:

  • 样例中启用 cpu/heap profiler:sudo yum install gperftools-devel
  • 运行测试:sudo yum install gtest-devel

4.2 使用 config_brpc.sh 编译 brpc

$ sh config_brpc.sh --headers="/usr/include" --libs="/usr/lib64 /usr/bin" $ make

与 Ubuntu 的差异在于--libs需要同时包含/usr/lib64(64 位库目录)与/usr/bin(用于定位 protoc 等可执行文件,见 config_brpc.sh 中find_bin的逻辑)。

其余选项与 Ubuntu 完全一致:--cxx=clang++ --cc=clang切换 clang,--nodebugsymbols去掉调试符号,--with-glog启用 glog,--with-thrift启用 thrift 支持。

运行样例

$ cd example/echo_c++ $ make $ ./echo_server & $ ./echo_client

动态链接方式同样为make clean后执行LINK_SO=1 make

运行测试

$ cd test $ make $ sh run_tests.sh

4.3 使用 cmake 编译 brpc

Fedora/CentOS 上的 CMake 路线与 Ubuntu 完全相同,直接参考第 3.3 节即可,此处不再赘述。

4.4 使用 vcpkg 编译 brpc

vcpkg 是一个全平台支持的 C++ 包管理器,也可以用它一键编译 brpc:

$ git clone https://github.com/microsoft/vcpkg.git $ ./bootstrap-vcpkg.bat # 使用 powershell $ ./bootstrap-vcpkg.sh # 使用 bash $ ./vcpkg install brpc

vcpkg 会自动处理 brpc 及其依赖的获取与构建,适合希望省去手工装依赖的开发者。

5. 自己构建依赖的 Linux

当发行版仓库中的依赖版本过旧,或需要自定义依赖(如自行编译 protobuf/leveldb)时,可以采用这种方式。

5.1 依赖准备

brpc 默认会构建出静态库和共享库两个版本,因此其依赖也需要同时具备静态库与共享库两种形态。以 gflags 为例,它默认不构建共享库,需要给 cmake 指定选项改变这一行为:

$ cmake . -DBUILD_SHARED_LIBS=1 -DBUILD_STATIC_LIBS=1 $ make

5.2 编译 brpc

假设 gflags 被克隆在../gflags_dev,进入 brpc 项目目录后运行:

$ sh config_brpc.sh --headers="../gflags_dev /usr/include" --libs="../gflags_dev /usr/lib64" $ make

这里给--headers--libs传递了多个路径,脚本会在这些位置递归检索依赖。你还可以把所有依赖连同 brpc 一起打包到一个目录中,然后把该目录传给--headers/--libs,脚本会递归搜索所有子目录直到找到必须的文件。这一点可以在 config_brpc.sh 的find_dir_of_libfind_dir_of_header等函数中看到实现——它们使用find -L ${LIBS_IN} -name "lib${1}.a" ...这样的递归查找方式。

官方给出的目录化组织示例:

$ ls my_dev gflags_dev protobuf_dev leveldb_dev brpc_dev $ cd brpc_dev $ sh config_brpc.sh --headers=.. --libs=.. $ make

其余开关(--cxx=clang++ --cc=clang--nodebugsymbols--with-glog--with-thrift)与前述一致。CMake 路线同样参考第 3.3 节。

6. macOS 编译指南

6.1 平台注意事项

  • 性能提示:在相同硬件条件下,macOS 版 brpc 的性能可能明显差于 Linux 版。如果你的服务是性能敏感的,请不要使用 macOS 作为生产环境。
  • Apple Silicon:master HEAD 已支持 M1 系列芯片,M2 未测试过,欢迎通过 issues 报告遗留的 warning/error。

6.2 依赖准备

brew install ./homebrew-formula/protobuf.rb brew install openssl git gnu-getopt coreutils gflags leveldb

注意这里特别安装了gnu-getoptcoreutils——因为 config_brpc.sh 在 Darwin 平台会检查getopt -V是否为 gnu-getopt 的实现(输出为" --"),同时需要 GNU 版realpath,缺少它们脚本会直接退出。

可选依赖:

  • 样例中启用 cpu/heap profiler:brew install gperftools
  • 运行测试需要 gtest。先运行brew install googletest看看 homebrew 是否支持(老版本没有);不支持则手动编译:
git clone https://github.com/google/googletest -b release-1.10.0 && cd googletest/googletest && mkdir build && cd build && cmake -DCMAKE_CXX_FLAGS="-std=c++11" .. && make

编译完成后,将include/lib/目录复制到/usr/local/include/usr/local/lib,以便所有应用都能使用 gtest。

6.3 OpenSSL 路径问题

Monterey 中 openssl 的安装位置可能不再位于/usr/local/opt/openssl,而可能在/opt/homebrew/Cellar目录下。如果编译时报告找不到 openssl:

  • 先运行brew link openssl --force,看看/usr/local/opt/openssl是否出现;
  • 没有的话自行设置软链:sudo ln -s /opt/homebrew/Cellar/openssl@3/3.0.3 /usr/local/opt/openssl。注意该命令中 openssl 的目录可能随环境变化,可通过brew info openssl查看实际路径。

实际上,config_brpc.sh 在 Darwin 平台会自动探测/usr/local/opt/openssl/opt/homebrew/Cellar两个位置并把它们加入头文件与库搜索路径,这为上述两种安装布局都提供了兜底。

6.4 使用 config_brpc.sh 编译 brpc

$ sh config_brpc.sh --headers=/usr/local/include --libs=/usr/local/lib --cc=clang --cxx=clang++ $ make

MacOS Monterey 下 brew 安装路径可能改变,如有路径相关错误,可尝试:

$ sh config_brpc.sh --headers=/opt/homebrew/include --libs=/opt/homebrew/lib --cc=clang --cxx=clang++ $ make

其余选项(--nodebugsymbols--with-glog--with-thrift)与前述一致。

运行样例

$ cd example/echo_c++ $ make $ ./echo_server & $ ./echo_client

动态链接同样用make clean+LINK_SO=1 make。注意 Darwin 平台下静态库.a必须在链接命令中显式给出,这一逻辑在 example/echo_c++/Makefile 中已有注释说明。

运行测试

$ cd test $ make $ sh run_tests.sh

6.5 使用 cmake 编译 brpc

参考第 3.3 节。CMake 在 Darwin 平台会自动把 OpenSSL 根目录指向/usr/local/opt/openssl(见 CMakeLists.txt),并链接 CoreFoundation、CoreGraphics 等系统框架(见 CMakeLists.txt)。

7. Docker 编译指南

使用 Docker 编译 brpc 可以完全隔离宿主环境差异:

$ mkdir -p ~/brpc $ cd ~/brpc $ git clone https://github.com/apache/brpc.git $ cd brpc $ docker build -t brpc:master . $ docker images $ docker run -it brpc:master /bin/bash

仓库根目录的 Dockerfile 给出了镜像内的构建过程佐证:它基于ubuntu:20.04,通过 apt 安装git g++ make libssl-dev libgflags-dev libprotobuf-dev libprotoc-dev protobuf-compiler libleveldb-dev libsnappy-dev等依赖,随后执行:

RUN cd brpc && sh config_brpc.sh --headers=/usr/include --libs=/usr/lib && \ make -j "$(nproc)"

也就是说,进入容器后 brpc 已完成编译,可以直接进入example/echo_c++运行样例,或继续执行测试。

8. 支持的依赖版本范围

brpc 对各依赖有明确的版本兼容区间,选择合适的版本能避免大量编译与运行期问题:

依赖支持版本备注
GCC4.8 - 11.2C++11 默认启用,以去除 boost 依赖(如 atomic);GCC7 中 over-aligned 问题暂时被禁止
Clang3.5 - 4.0无已知问题
glibc2.12 - 2.25无已知问题
protobuf3.0 - 3.251.8.0 版本引入部分 proto3 语法后不再兼容 pb 2.x;pb 3.x 的 Arena 至今未被支持
gflags2.0 - 2.2.1无已知问题
openssl0.97 - 1.1被 https 功能需要
tcmalloc1.7 - 2.5brpc 默认链接 tcmalloc,用户按需链接
glog3.3+与 brpc 默认日志实现冲突,二选一
valgrind3.8+brpc 自动检测 valgrind 并注册 bthread 栈
thrift0.9.3 - 0.11.0无已知问题

几个需要重点展开的版本注意事项:

8.1 GCC 版本细节

  • C++11 默认启用,因此编译器最低要求为支持 C++11 的版本(config_brpc.sh 与 CMakeLists.txt 都会在 GCC 低于 4.8 时直接报错退出)。
  • 请在 makefile 的 cxxflags 中增加-D__const__=__unused__选项,以避免 gcc4+ 中的 errno 问题。这一宏实际上已被 config_brpc.sh 与 CMakeLists.txt 自动加入 CPPFLAGS,源码注释明确说明这是为了避免 GCC>=4.8 对 TLS 变量的过度优化(对应上游 issue #1693)。
  • 使用其他版本的 gcc 可能会产生编译警告,可联系社区修复。

8.2 protobuf 版本边界

1.8.0 版本中相关 PR 引入了部分 proto3 语法,因此目前 brpc 不再兼容 pb 2.x 版本;如果你希望使用 pb 2.x,需要使用 1.8.0 之前的 brpc 版本。另外,从 config_brpc.sh 的源码可以看到,当探测到 protobuf 版本>= 4.22GOOGLE_PROTOBUF_VERSION >= 4022000)时,脚本会自动要求并链接一长串absl_*目标库(absl_strings、absl_sync 等),同时把标准切换到 C++17;否则使用-std=c++0x。这一自适应逻辑在 CMakeLists.txt 中也有对应实现。这意味着:高版本 protobuf(4.21+)会引入 abseil 依赖,你需要同时安装 abseil 库

8.3 tcmalloc 的使用陷阱

brpc 默认链接 tcmalloc,用户按需自行链接。tcmalloc 与 glibc 内置 ptmalloc 相比通常能提升性能,但不同版本的 tcmalloc 表现可能迥异,例如 tcmalloc 2.1 与 1.7、2.5 相比,可能让 brpc 多线程样例性能显著恶化(由 tcmalloc 中的一个自旋锁导致),甚至小版本号之间表现也不同。当程序表现不符合预期时,移除 tcmalloc 再尝试其他版本。

用 gcc 4.8.2 编译然后链接更早版本 GCC 编译的 tcmalloc,可能会让程序在main()函数之前挂掉或死锁:

遇到此类问题时,请用同一个 GCC 重新编译 tcmalloc。

另一个常见问题是:tcmalloc 不会像 ptmalloc 一样及时把内存归还给系统。因此当发生无效内存访问时,程序可能不会直接挂掉,而是可能在不相关的位置挂掉,甚至一直不挂。当程序出现怪异的内存问题时,优先尝试移除 tcmalloc。

如果要使用 cpu profiler 或 heap profiler,需要链接libtcmalloc_and_profiler.a——这两个 profiler 都基于 tcmalloc 实现;而 contention profiler 不需要 tcmalloc。移除 tcmalloc 时,不仅要移除 tcmalloc 的链接,也要移除宏-DBRPC_ENABLE_CPU_PROFILER

8.4 glog 与默认日志的取舍

brpc 实现了一个默认的日志功能(源码位于 src/butil/logging.h),它与 glog 冲突。要替换成 glog,可以给config_brpc.sh增加--with-glog选项,或给 cmake 增加-DWITH_GLOG=ON选项。切换后,src/butil/config.h中的BRPC_WITH_GLOG宏会被置为 1,brpc 的日志调用会改走 glog 实现。

8.5 其他依赖

  • openssl:被 https 功能需要,版本范围 0.97 - 1.1(更现代的版本亦可,以实际编译结果为准)。
  • valgrind:brpc 会自动检测 valgrind(随后注册 bthread 栈),不支持老版本(如 3.2)。
  • thrift:支持 0.9.3 - 0.11.0。从 config_brpc.sh 可以看到,启用--with-thrift后会追加-DENABLE_THRIFT_FRAMED_PROTOCOL宏并链接libthriftnb(必要时附带-levent -lthrift),还会根据 thrift 版本判断是否定义_THRIFT_VERSION_LOWER_THAN_0_11_0_以适配 API 差异。

9. 实例追踪:trackme_server

在构建与部署之外,brpc 还提供了一个实例追踪工具,帮助你在生产环境中定位和监控所有 brpc 实例。

使用方法很简单:

  1. 在某处运行 tools/trackme_server;
  2. 启动需要被追踪的 brpc 实例时加上-trackme_server=SERVER参数;
  3. trackme_server 会周期性地从各实例收到 ping 消息并打印日志;
  4. 你可以从日志中聚合出所有实例的地址,再调用实例的内置服务(如 /status、/vars、/connections 等,参见 builtin_service)获取更多运行信息。

这一机制适用于服务实例数量较多、需要统一盘点与健康巡检的部署场景,配合 brpc 自带的监控体系可以快速建立实例清单。

10. 快速排查清单

把前面各节的易错点汇总为一份自查清单,便于编译失败时快速定位:

  1. 依赖不齐:确认 gflags、protobuf(含 protoc)、leveldb 均已安装;高版本 protobuf 需额外安装 abseil。
  2. --cc/--cxx必须成对出现:只设置其中一个,config_brpc.sh 会直接报错退出。
  3. macOS 缺少 gnu-getopt/coreutilsconfig_brpc.sh在 Darwin 平台强制要求它们,否则脚本报错。
  4. openssl 找不到:macOS 下优先brew link openssl --force,失败则手动软链到/usr/local/opt/openssl
  5. leveldb 静态链接失败:通过源码编译 leveldb 时务必加-DCMAKE_POSITION_INDEPENDENT_CODE=ON,并安装 snappy。
  6. 编译选项改动后缓存残留:切换 CMake 选项(如LINK_SOWITH_DEBUG_SYMBOLS)前先删除build/CMakeCache.txt;切换样例链接方式前先make clean
  7. 程序在 main 之前挂掉/死锁:大概率是 tcmalloc 与 GCC 版本不匹配,用同一 GCC 重编 tcmalloc,或直接移除 tcmalloc。
  8. 性能异常:先检查是否链接了表现不佳的 tcmalloc 版本(如 2.1),替换或移除后对比。
  9. 生产环境性能敏感:避免在 macOS 上部署 brpc 服务。

通过以上九个检查点,配合 config_brpc.sh 生成的config.mksrc/butil/config.h进行核对,绝大多数构建问题都能在几分钟内定位解决。

【免费下载链接】brpcbrpc is an Industrial-grade RPC framework using C++ Language, which is often used in high performance system such as Search, Storage, Machine learning, Advertisement, Recommendation etc. "brpc" means "better RPC".项目地址: https://gitcode.com/gh_mirrors/brpc6/brpc

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询