SRS的日志文件模块SrsFileLog—SRS源码分析

作者:罗上文,微信:Loken1,公众号:FFmpeg弦外之音

关于 SRS 日志的基本介绍以及 切割等功能,请阅读 SRS 官方文档《日志》与《日志切割》。本文主要讲解 SRS 日志模块的代码实现

SRS 日志模块的实现类是 SrsFileLog,如下:

class SrsFileLog : public ISrsLog, public ISrsReloadHandler
{
private:
    // Defined in SrsLogLevel.
    SrsLogLevel level_;
private:
    char* log_data;
    ...省略...

可以看到,SrsFileLog 继承了 两个接口(Interface),ISrsLogISrsReloadHandlerISrsLog 接口比较简单,这里就不说了。

我们重点讲一下 ISrsReloadHandler 这个接口,SrsFileLog 为什么要继承 ISrsReloadHandler ,如果不继承会有什么问题?

我们直接把继承删掉,看看编译会不会报错,如下:

1-1

我们 make 编译一下,会报以下错误。

1-2

通过这种方式,我们排查到了 SrsFileLog 使用到 ISrsReloadHandler 的地方。


我估计他的用法与逻辑是这样的,SrsFileLog 里面有一些日志文件存储路径,存储方式等配置,这些配置可以通过 reload srs.conf 文件来重新加载的。SRS 重新加载配置文件的命令如下:

./etc/init.d/srs reload

srs.conf 的配置怎么修改到 SrsFileLog 里面呢?答:通过 subscribe 接口,SrsConfig 模块提供了一个 subscribe 函数来注册外部的模块,如下:

1-3

subscribes 变量是一个 vector 来的。

// The reload subscribers, when reload, callback all handlers.
std::vector<ISrsReloadHandler*> subscribes;

然后他在哪里使用这个 vector 呢?

答:在 do_reload_listen()do_reload_max_connections() 等函数里面如下:

1-4

这个配置 reload 的整体逻辑是这样的,会有一个协程 SrsSignalManager::cycle() 在阻塞不断读取信号事件,当产生了 reload 信号,就会调 server->on_signal() 来处理信号。经过多层函数调用之后,最后会遍历每一个 订阅者(subscriber)来执行各种 reload 方法。


但是我测试下来,虽然 SrsFileLog 继承了 ISrsReloadHandler ,但是他并没有实现接口里的任何一个方法,我测试了一下修改 srs.confsrs_log_level 配置,如下:

srs_log_level info
修改为
srs_log_level error

然后执行 ./etc/init.d/srs reload,发现这个 srs_log_level 的修改并没有生效,还是 SrsLogLevelInfo 。如下:

1-5

提示:_srs_log 是一个全局变量。

所以如果你想 日志相关的配置 能支持 reload,需要自己往 ISrsReloadHandler 加函数,然后在 SrsFileLog 里实现它。


SrsFileLog 类里面的其他方法相对来说比较简单,读者执行阅读源码就行,他的注释也非常全。


版权所属 xianwanzhiyin.net 罗上文 2023 all right reserved,powered by Gitbook该文件修订时间: 2024-01-08 01:12:45

results matching ""

    No results matching ""