Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
172 changes: 100 additions & 72 deletions unitest/log_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,96 +15,124 @@ See the Mulan PSL v2 for more details. */
#include "log_test.h"

#include "gtest/gtest.h"

#include "common/log/log.h"
#include "common/file/file.h" // 引入文件操作工具类(miniob 已有封装)
#include <cassert>
#include <string>
#include <unistd.h> // 用于 sleep 等待日志刷盘

using namespace common;

LogTest::LogTest()
{
// Auto-generated constructor stub
}

LogTest::~LogTest()
{
// Auto-generated destructor stub
}
// 测试用日志文件路径(统一管理,避免硬编码)
const std::string TEST_LOG_FILE = "./test_logrotate.log";
const size_t LOG_ROTATE_SIZE = 1024 * 1024; // 1MB 轮转阈值(与日志模块默认配置一致)

int LogTest::init(const std::string &logFile)
{
LogTest::LogTest() = default; // 简化默认构造函数(使用编译器生成版本)
LogTest::~LogTest() = default; // 简化析构函数

LoggerFactory::init_default(logFile);
/**
* @brief 初始化日志模块
* @param log_file 日志文件路径(默认使用测试专用路径)
* @return 0 成功,非0 失败
*/
int LogTest::init(const std::string &log_file = TEST_LOG_FILE) {
// 初始化前先清理历史测试日志(避免干扰)
FileUtil::delete_file(log_file);
FileUtil::delete_file(log_file + ".1"); // 清理轮转后的旧日志

LoggerFactory::init_default(log_file);
g_log->set_rotate_type(LOG_ROTATE_BYSIZE);

g_log->set_rotate_size(LOG_ROTATE_SIZE); // 显式设置轮转大小(确保测试一致性)
return 0;
}

void *LogTest::log_loop(void *param)
{
int index = *(int *)param;
int i = 0;
while (i < 100) {
i++;
LOG_INFO("index:%d --> %d", index, i);
/**
* @brief 日志循环输出线程函数
* @param param 线程参数(指向 int 类型的日志标识索引)
* @return 无
*/
void *LogTest::log_loop(void *param) {
// 空指针校验(修复内存安全隐患)
if (param == nullptr) {
LOG_ERROR("log_loop: input param is null");
return nullptr;
}

return NULL;
}

void checkRotate()
{
LogTest test;

test.init();
ASSERT_EQ(g_log->get_rotate_type(), LOG_ROTATE_BYSIZE);

int index = 30;
test.log_loop(&index);
}

TEST(checkRotateTest, CheckRoateTest)
{
checkRotate();
int thread_index = *(static_cast<int *>(param)); // 类型安全转换
// 输出足够多日志,确保触发大小轮转(原100条可能不足1MB)
for (int i = 0; i < 10000; ++i) {
LOG_INFO("Thread-%d: log count = %d, test log rotate by size", thread_index, i);
}
return nullptr;
}

void testEnableTest()
{
LogTest test;

test.init();

ASSERT_EQ(g_log->check_output(LOG_LEVEL_PANIC, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_ERR, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_WARN, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_INFO, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_DEBUG, __FILE__), false);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_TRACE, __FILE__), false);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_LAST, __FILE__), false);

g_log->set_default_module(__FILE__);

ASSERT_EQ(g_log->check_output(LOG_LEVEL_PANIC, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_ERR, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_WARN, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_INFO, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_DEBUG, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_TRACE, __FILE__), true);
ASSERT_EQ(g_log->check_output(LOG_LEVEL_LAST, __FILE__), true);
/**
* @brief 测试日志按大小轮转功能
* 验证点:1. 轮转配置生效;2. 日志文件生成;3. 达到阈值后触发轮转
*/
TEST(LogRotateTest, RotateBySize) {
LogTest log_test;
ASSERT_EQ(log_test.init(), 0) << "日志模块初始化失败";

// 验证轮转配置
ASSERT_EQ(g_log->get_rotate_type(), LOG_ROTATE_BYSIZE) << "日志轮转类型配置错误";
ASSERT_EQ(g_log->get_rotate_size(), LOG_ROTATE_SIZE) << "日志轮转大小配置错误";

// 启动单线程输出日志(确保触发轮转)
int thread_index = 1;
log_test.log_loop(&thread_index);

// 等待日志刷盘(避免异步写入导致文件未生成)
sleep(1);

// 验证日志文件存在
ASSERT_TRUE(FileUtil::file_exists(TEST_LOG_FILE)) << "主日志文件未生成";
ASSERT_TRUE(FileUtil::file_exists(TEST_LOG_FILE + ".1")) << "日志未触发轮转(未生成轮转文件)";

// 验证轮转文件大小符合阈值(允许±10%误差)
size_t rotate_file_size = FileUtil::file_size(TEST_LOG_FILE + ".1");
ASSERT_GE(rotate_file_size, LOG_ROTATE_SIZE * 0.9) << "轮转文件大小未达到阈值";
ASSERT_LE(rotate_file_size, LOG_ROTATE_SIZE * 1.1) << "轮转文件大小超出阈值过多";

// 清理测试资源
LoggerFactory::destroy();
FileUtil::delete_file(TEST_LOG_FILE);
FileUtil::delete_file(TEST_LOG_FILE + ".1");
}

TEST(testEnableTest, CheckEnableTest)
{
testEnableTest();
/**
* @brief 测试日志级别启用/禁用功能
* 验证点:1. 默认模块日志级别;2. 指定模块日志级别;3. 非法级别校验
*/
TEST(LogLevelTest, CheckEnableStatus) {
LogTest log_test;
ASSERT_EQ(log_test.init(), 0) << "日志模块初始化失败";
const char *test_module = __FILE__;

// 验证默认模块的日志级别(默认只启用 INFO 及以上)
ASSERT_TRUE(g_log->check_output(LOG_LEVEL_PANIC, test_module)) << "PANIC 级别应默认启用";
ASSERT_TRUE(g_log->check_output(LOG_LEVEL_ERR, test_module)) << "ERR 级别应默认启用";
ASSERT_TRUE(g_log->check_output(LOG_LEVEL_WARN, test_module)) << "WARN 级别应默认启用";
ASSERT_TRUE(g_log->check_output(LOG_LEVEL_INFO, test_module)) << "INFO 级别应默认启用";
ASSERT_FALSE(g_log->check_output(LOG_LEVEL_DEBUG, test_module)) << "DEBUG 级别应默认禁用";
ASSERT_FALSE(g_log->check_output(LOG_LEVEL_TRACE, test_module)) << "TRACE 级别应默认禁用";
ASSERT_FALSE(g_log->check_output(LOG_LEVEL_LAST, test_module)) << "非法级别应返回禁用";

// 验证指定模块启用所有日志级别
g_log->set_default_module(test_module);
ASSERT_TRUE(g_log->check_output(LOG_LEVEL_DEBUG, test_module)) << "指定模块应启用 DEBUG 级别";
ASSERT_TRUE(g_log->check_output(LOG_LEVEL_TRACE, test_module)) << "指定模块应启用 TRACE 级别";

// 验证非默认模块的日志级别(仍遵循默认配置)
const char *other_module = "other_test_module";
ASSERT_FALSE(g_log->check_output(LOG_LEVEL_DEBUG, other_module)) << "非默认模块应禁用 DEBUG 级别";

// 清理测试资源
LoggerFactory::destroy();
FileUtil::delete_file(TEST_LOG_FILE);
}

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

// 分析gtest程序的命令行参数
int main(int argc, char **argv) {
testing::InitGoogleTest(&argc, argv);

// 调用RUN_ALL_TESTS()运行所有测试用例
// main函数返回RUN_ALL_TESTS()的运行结果
return RUN_ALL_TESTS();
}
}