QLog专题-Delphi/C++ Builder下的跨平台异步日志记录单元

QLog 是一个异步的日志记录引擎,由于不是同步记录日志内容,在程序被强行中止(含由于程序自身原因或被外部管理工具)时,会丢失部分日志内容。

QLog 的日志记录支持 syslogd 协议,因此,任何基于 syslogd 协议的日志服务器都可以接收并存贮由 QLog 发送的日志信息。

QLog 之所以采用异步的方式记录日志,是因为采用异步的方式的记录日志可以最大限度的降低由于日志记录需要的 IO 操作时间较长影响业务逻辑执行效率的问题。

QLog 记录日志的方式比较简单直接:

第一步,要引用 QLog 单元:

【Delphi】

【C++ Builder】

注意,由于QLog 的全局实例一般在程序启动时就创建,所以 QLog 是通过编译条件来控制日志记录的设置。具体的条件编译选项均位于QLog 单元:

  • QLOG_CREATE_GLOBAL

此选项控制是否自动创建默认的全局日志记录变量,如果不定义该条件编译变量,则你需要自己在合理的时机创建 TQLog 类型的实例赋给 Logs 这个全局变量。如果不赋给默认的 Logs 实例,就不能使用默认的接口,而只能使用你自己创建 TQLog 类型实例的类方法来记录日志。

  • QLOG_CREATE_DEFAULT_WRITER

此选项控制是否创建默认的文件类型日志记录单元,它只有在 QLOG_CREATE_GLOBAL 启用时才有意义。注意,在移动平台上,默认它是关闭的。移动平台建议创建 TQLogSocketWriter 实例来使用 syslogd 协议来传送日志到日志服务器程序。

  • RENAME_HISTORY

此选项控制在启动时,如果默认日志文件名存在,是否将其压缩打包。如果未定义,则会直接将重名的日志文件内容清空,重新记录。

第二步:如果创建了默认的 Logs 实例,那么在 Delphi 中就可以直接调用 PostLog ,而在 C++ Builder 中,则提供了一个额外的名为 AddLog 的函数以方便使用参数化日志记录。

以上就是 QLog 的常规用法了。

【提示】

1、不使用默认的日志文件名来记录日志

默认的 TQLogFileWriter 创建的日志文件使用当前可执行文件的文件名做为日志文件名,如当前程序是 a.exe,则对应的日志文件为a.log,而且被存贮在当前应用程序目录下。如果要改变这一行为,就需要自己创建 TQLogFileWriter 实例来替换默认的 TQLogFileWriter 实例。

首先,注释掉条件编译选项 QLOG_CREATE_DEFAULT_WRITER ,以避免创建默认的日志文件。然后创建自己的 TQLogFileWriter 实例,并将日志文件名做为参数传递到构造函数中。

【Delphi】

【C++ Builder】

这样子,日志文件就会在指定的目录下创建并记录日志。

2、使用 TQLogSocketWriter 作为日志记录器

TQLogSocketWriter 用于将日志写入到远程的日志服务器,服务器只要兼容 syslogd 协议即可接收到相关的日志内容。参考代码如下:

【Delphi]

【C++ Builder】

由于一般的 syslogd 服务器使用的都是 UDP 协议,所以 TQLogSocketWriter 默认情况下,UseTCP 属性都是 false,如果你要使用 TCP 协议传输,则请设置 UseTCP 为 True 即可。

3、如何控制启动日志文件压缩?

QLog 通过 MaxLogFileSize 全局变量来控制启动后台压缩的日志文件大小,只有日志文件内容大小达到这个上限值时,才会在后台启动压缩线程,对日志内容进行压缩打包,以避免日志文件占用过多的空间。这个值如果小于 0 ,则认为始终不压缩日志。默认值为-1,你只需要修改为自己认为合适的一个值即可,作者推荐是 2097152 (2MB),当日志每达到 2MB  时,就将历史日志打包压缩并创建新日志文件来记录后续日志内容。

4、为什么不支持日志的同步写入?

目前版本的 QLog 暂不会支持(虽然已经定义了有关的一些项目),主要是因为同步记录日志的需要的情况很少,而且强制同步日志记录会由于 IO 操作而拖慢程序的效率。

5、我能否同时支持将日志写入文件和远程日志服务器?

当然,你甚至可以同时添加多个服务器和文件,只需要创建对应的 TQLogWriter 子类实例,并将其加入到 Logs 的 Castor 列表中即可。

分享到:
  1. 其实一直希望每次不要重新创建新的文件,而是用之前的,一直追加,直到大小到了设定的再压缩创建新的!