微服务即时通信系统---(二)框架学习

news/2025/2/22 6:08:32

目录

gflags

介绍

安装

使用

头文件包含

编译时指明库 

宏定义参数

启动时设置命令行参数来设置参数值

 使用配置文件来设置参数值

初始化所有参数

访问参数

程序B访问程序A定义的参数

gflags提供的特殊参数标识 

 使用案例

代码编写 

样例运行

gtest

介绍

安装

使用

头文件包含

编译时指明库

gtest框架初始化接口

测试样例TEST宏

断言宏

使用案例

代码编写

 样例运行

spdlog

介绍

安装

使用

头文件包含

编译时指明库

日志输出等级

日志记录器类

日志输出格式自定义

异步日志记录类

日志记录器工厂类

创建日志器函数

日志器封装

日志器封装测试

etcd

介绍

安装

节点配置

运行验证

插入一个数据

获取数据

删除数据

删除所有数据

使用etcd搭建项目的服务注册与发现中心

etcd-cpp-apiv3

github地址

安装依赖

api框架安装

 头文件包含以及编译时指明库

客户端类与接口介绍

Client

Response

Value

Event

KeepAlive

Watcher

各个类的作用以及各自的关系

简单使用样例代码

put

get

Makefile

运行结果

服务注册与服务发现代码封装


本章主要是学习和使用本项目中所需使用到的一些框架

gflags

介绍

gflags是google开发的一个开源库,用于C++程序中命令行参数的声明、定义和解析。

gflags提供了一种简单的方式来添加、解析和文档化命令行标志,使得程序可以根据不同的运行时配置来调整。

gflags的特点:

易于使用 提供了一套简单直观的API来定义和解析命令行标志。
自动帮助和文档 gflags可以自动生成每个标志的帮助信息和文档。
类型安全 gflags支持多种数据类型的标志,包括布尔值、整数、字符串等,并且提供了类型转换和检查。
多平台性 可以在多种操作系统上使用,如Windows、Linux。
可扩展性 允许开发者自定义标志的注册和解析逻辑。

安装

命令安装:

sudo apt-get install libgflags-dev

使用

头文件包含

#include <gflags/gflags.h>

编译时指明库 

-l gflags

 例如写Makefile时:

g++ $^ -o $@ -std=c++17 -lgflags

宏定义参数

gflags提供了它自己的宏,让我们来定义参数。该宏有三个参数:参数名、参数默认值、参数说明(注释)。

其中gflags支持的宏定义类型:

DEFINE_bool
DEFINE_int32
DEFINE_int64
DEFINE_uint64
DEFINE_double
DEFINE_string

使用样例:

DEFINE_bool(reuser_addr, true, "是否启动地址重用, 默认: yes");
DEFINE_int32(log_level, 1, "日志等级: 1-DEBUG, 2-WARN, 3-ERROR");
DEFINE_string(log_file, "stdout", "日志输出文件, 默认: stdout");

启动时设置命令行参数来设置参数值

gflags为我们提供了多种设置命令行参数的方式,支持我们在运行程序的时候,以命令行参数的形式传入参数的值。

注意:这里不是定义新的参数,而是设置我们已经定义号的参数的值!

shell: ./a.out exec --log_level=2
shell: ./a.out exec --log_file="stderr"
shell: ./a.out exec --reuse_addr=false

 使用配置文件来设置参数值

除了使用命令行参数的形式来设置参数值,也可以、更推荐使用配置文件的方式来设置参数值。

main.conf:

-reuse_addr=false
-log_level=2
-log_file="stderr"

此时运行程序的时候,需要指定该程序从哪个配置文件里读取参数:

-flagfile=xxx #从xxx这个配置文件中读取参数

同样注意:配置文件中的参数名也必须和代码中定义的参数名一样。 

初始化所有参数

当我们定义好参数后,并不能直接使用,需要用gflags提供的API将我们定义的参数进行初始化解析后,才能正常使用。

int main(int argc, char *argv[])
{
    google::ParseCommandLineFlags(&argc, &argv, true);
}

其中argc和argv就是main函数的参数。

第三个参数称为remove_flags。true:在解析命令行参数后,argc和argv会被修改,移除已解析的标志。这意味着后续代码将无法再访问这些标志,因为它们已经从argv中移除。

比如上述定义的reuse_addr,如果这里我们用的true,那么在解析之后,argv中将不再含有 --reuse_addr的标志。

true:通常在你希望清理命令行参数,使得后续代码不会误处理这些标志时使用。

访问参数

在程序中不能直接按照变量名去使用参数,gflags规定,在使用其定义的参数时,必须加上前缀FLAGS_来使用。

FLAGS_reuse_addr;
FLAGS_log_level;
FLAGS_log_file;

程序B访问程序A定义的参数

在程序B中想要访问程序A的参数,需要先声明。

gflags提供了宏DECLARE来声明参数。

DECLARE_bool(reuse_addr);
DECLARE_int32(log_level);
DECLARE_string(log_file);

gflags提供的特殊参数标识 

--help 显示文件中所有标识的帮助信息
--helpfull 比--help显示的信息更加全面
--helpshort 只显示当前执行文件里的标志
--helpxml 以XML方式进行打印,方便处理
--version 打印版本信息,由google::SetVersionString()设定
--flagfile 指定配置文件

 使用案例

代码编写 

main.cc

#include <gflags/gflags.h>
#include <iostream>

DEFINE_bool(reuser_addr, true, "是否启动地址重用, 默认: yes");
DEFINE_int32(log_level, 1, "日志等级: 1-DEBUG, 2-WARN, 3-ERROR");
DEFINE_string(log_file, "stdout", "日志输出文件, 默认: stdout");

int main(int argc, char *argv[])
{
    google::ParseCommandLineFlags(&argc, &argv, true);
    std::cout << "reuse: " << FLAGS_reuser_addr << std::endl;
    std::cout << "log_level: " << FLAGS_log_level << std::endl;
    std::cout << "log_file: " << FLAGS_log_file << std::endl;
    return 0;
}

 配置文件main.conf

-reuse_addr=false
-log_level=3
-log_file="stderr"

Makefile

main:main.cc
	g++ $^ -o $@ -std=c++17 -lgflags

样例运行

shell$ ./main --flagfile=main.conf
reuse: 1
log_level: 3
log_file: "stderr"

gtest

介绍

gtest是一个google开发的跨平台的C++单元测试框架,是为了在不同的平台上为编写C++单元测试而生成的。

它提供了丰富的断言、致命和非致命判断、参数化等等测试所需要的宏,以及全局测试、单元测试组件。

安装

命令安装:

sudo apt-get install libgtest-dev

使用

头文件包含

#include <gtest/gtest.h>

编译时指明库

-l gtest

gtest框架初始化接口

想要使用gtest进行单元测试之前,必须进行框架的初始化。

int main(int argc, char *argv[])
{
    testing::InitGoogleTest(&argc, argv);
    return 0;
}

测试样例TEST宏

TEST(测试名称, 测试样例)
TEST_F(test_fixture, test_name)

TEST:主要用来创建一个简单测试,定义一个测试函数。

TEST_F:主要用来进行多样测试,适用于多个测试场景如果需要相同的数据配置的情况。

断言宏

gtest中的断言宏一般分为两类。

ASSERT_系列:如果当前点检测失败,就退出当前函数。

EXPECT_系列:如果当前点检测失败,继续向下执行。

经常使用的断言介绍:

ASSERT_TRUE(x) 期待x的结果是true
ASSERT_FALSE(x) 期待x的结果是false
ASSERT_EQ(a , b) 期待a 等于b
ASSERT_NE(a, b) 期待a 不等于 b
ASSERT_LT(a, b) 期待a 小于 b
ASSERT_GT(a , b) 期待 a 大于b
ASSERT_LE(a , b) 期待 a 小于等于b
ASSERT_GE(a , b) 期待 a大于等于 b

使用案例

代码编写

main.cc

#include <gtest/gtest.h>
#include <iostream>

int abs(int x)
{
    return x > 0 ? x : -x;
}

TEST(abs_test, test1)
{
    ASSERT_TRUE(abs(1) == 1) << "abs(1)=1";
    ASSERT_TRUE(abs(-1) == 1);
    ASSERT_FALSE(abs(-2) == -2);
    ASSERT_EQ(abs(1), abs(-1));
    ASSERT_NE(abs(-1), 0);
    ASSERT_LT(abs(-1), 2);
    ASSERT_GT(abs(-1), 0);
    ASSERT_LE(abs(-1), 2);
    ASSERT_GE(abs(-1), 0);
}

int main(int argc, char *argv[])
{
    testing::InitGoogleTest(&argc, argv);
    RUN_ALL_TESTS();
    return 0;
}

Makefile

main:main.cc
	g++ $^ -o $@ -std=c++17 -lgtest

 样例运行

shell $ ./main 
[==========] Running 1 test from 1 test suite.
[----------] Global test environment set-up.
[----------] 1 test from abs_test
[ RUN      ] abs_test.test1
[       OK ] abs_test.test1 (0 ms)
[----------] 1 test from abs_test (0 ms total)

[----------] Global test environment tear-down
[==========] 1 test from 1 test suite ran. (0 ms total)
[  PASSED  ] 1 test.

spdlog

介绍

spdlog是一个高性能、超快速、零配置的C++日志库,旨在提供简洁的API和丰富的功能,同时保持高性能的日志记录。

它支持多种输出目标、格式化选项、线程安全以及异步日志记录。

spdlog的特点:

高性能 spdlog专为速度而设计,即时在高负载的情况下也能保持良好的性能。
零配置

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

相关文章

Minio分布式多节点多驱动器集群部署

Minio分布式多节点多驱动器集群部署 Minio分布式多节点多驱动器集群部署节点规划先决条件开放防火墙端口设置主机名更新域名映射文件时间同步存储要求内存要求 增加虚拟机磁盘(所有机器都要执行)部署分布式 MinIO测试上传与预览测试高可用MinIO 配置限制模拟单节点磁盘故障模拟…

网络空间安全(1)web应用程序的发展历程

前言 Web应用程序的发展历程是一部技术创新与社会变革交织的长卷&#xff0c;从简单的文档共享系统到如今复杂、交互式、数据驱动的平台&#xff0c;经历了多个重要阶段。 一、起源与初期发展&#xff08;1989-1995年&#xff09; Web的诞生&#xff1a; 1989年&#xff0c;欧洲…

深蕾科技智能多媒体SoC产品助力“DataEye剧查查之夜”微短剧盛会

深蕾科技助力微短剧盛会 深圳湾“DataEye剧查查之夜”微短剧盛会&#xff0c;于2025年2月20日18:00点&#xff0c;在深圳湾盛大开启。作为第十四届中国国际新媒体短片节的重要组成部分&#xff0c;“剧查查之夜”汇聚了微短剧行业的顶尖力量&#xff0c;吸引了众多大咖齐聚一堂…

ip属地是电话号码吗怎么改

在数字化时代&#xff0c;IP属地作为网络身份的一部分&#xff0c;对于许多互联网用户来说并不陌生。然而&#xff0c;关于IP属地的具体含义以及如何更改它&#xff0c;却常常让一些用户感到困惑。特别是当提到IP属地与电话号码之间的关系时&#xff0c;更是容易让人产生误解。…

超多目标优化:基于导航变量的多目标粒子群优化算法(NMOPSO)的无人机三维路径规划,MATLAB代码

一、基于导航变量的多目标粒子群优化算法&#xff08;NMOPSO&#xff09;介绍 基于导航变量的多目标粒子群优化算法&#xff08;Navigation variable-based multi-objective particle swarm optimization&#xff0c;NMOPSO&#xff09;是2025年提出的一种用于无人机路径规划的…

【第三节】C++设计模式(创建型模式)-单例模式

目录 一、模式价值与核心思想 二、现代化实现方案 2.1 核心差异对比表 2.2 典型代码实现 2.3 工程场景选择指南 2.4 关键问题深度解析 2.5 现代C最佳实践 2.6 总结 三、模式演进与替代方案 四、最佳实践建议 一、模式价值与核心思想 单例模式&#xff08;Singleton P…

【Gin-Web】Bluebell社区项目梳理1:注册业务、登录业务流程及代码

本文目录 一、Web的CLD分层架构、二、注册业务流程三、登录业务流程四、Token认证模式基于Cookie和Seesion的认证模式 五、分布式ID生成与雪花算法 一、Web的CLD分层架构、 一般Web项目可以看作是CLD架构&#xff0c;也就是图中所示&#xff0c;ControllerLogicDAO层&#xff…

图数据库Neo4j面试内容整理-建模实践

在 Neo4j 中进行图数据建模(Graph Modeling)是设计和构建高效图数据库系统的关键。图数据库与关系型数据库不同,图数据建模强调的是如何通过节点、关系、标签和属性来表示和组织数据之间的复杂联系。因此,图数据库的建模过程不仅需要理解数据本身,还需要考虑查询的效率和扩…