log4c日誌庫的用法,再封裝及其完整例子
找了多篇文章,發現都講的不怎麼簡明。自己摸索了下,記錄如下:
Log4c中有三個重要的概念, Category, Appender, Layout。
Category用於區分不同的Logger, 其實它就是個logger。在一個程式中我們可以通過Category來指定很多的Logger,用於不同的目的。Appdender用於描述輸出流,通過為Category來指定一個Appdender,可以決定將log資訊來輸出到什麼地方去,比如stdout, stderr, 檔案, 或者是socket等等
Layout用於指定日誌資訊的格式,通過為Appender來指定一個Layout,可以決定log資訊以何種格式來輸出,比如是否有帶有時間戳, 是否包含檔案位置資訊等,以及他們在一條log資訊中的輸出格式的等。
例子:
系統:ubuntu12.10 .
準備:
安裝log4c庫, sudo apt-get install liblog4c-dev liblog4c-doc
檔案:
log.h log.c 自己將log4c重新封裝的函式
test-log.c 測試用的主函式
log4crc 配置檔案(xml,照著寫就行)
//log.h
//log.c#ifndef _LOG_H_ #define _LOG_H_ #include <string.h> #include <stdlib.h> #ifdef __cplusplus extern "C" { #endif #include "log4c.h" #ifdef __cplusplus } #endif #define LOG_PRI_ERROR LOG4C_PRIORITY_ERROR #define LOG_PRI_WARN LOG4C_PRIORITY_WARN #define LOG_PRI_NOTICE LOG4C_PRIORITY_NOTICE #define LOG_PRI_DEBUG LOG4C_PRIORITY_DEBUG #define LOG_PRI_TRACE LOG4C_PRIORITY_TRACE extern int log_open(const char *category); extern void log_message(int priority ,const char* fmt, ...); extern void log_trace(const char *file , int line , const char *func, const char *fmt ,...); extern int log_close(); #define LOG_ERROR(fmt , args...) \ log_message(LOG_PRI_ERROR, fmt, ##args) #define LOG_WARN(fmt, args...) \ log_message(LOG_PRI_WARN, fmt , ##args) #define LOG_NOTICE(fmt , args...) \ log_message(LOG_PRI_NOTICE, fmt , ##args) #define LOG_DEBUG(fmt , args...) \ log_message(LOG_PRI_DEBUG, fmt , ##args) #define LOG_TRACE(fmt,args...) \ log_trace(__FILE__ , __LINE__ , __FUNCTION__ , fmt ,## args) #endif
#include <log4c.h> #include <assert.h> #include "log.h" static log4c_category_t *log_category = NULL; int log_open(const char *category) { if (log4c_init() == 1) { return -1; } log_category = log4c_category_get(category); return 0 ; } void log_message(int priority , const char *fmt , ...) { va_list ap; assert(log_category != NULL); va_start(ap, fmt); log4c_category_vlog(log_category , priority , fmt , ap); va_end(ap); } void log_trace(const char *file, int line, const char *fun, const char *fmt , ...) { char new_fmt[2048]; const char *head_fmt = "[file:%s, line:%d, function:%s]"; va_list ap; int n; assert(log_category != NULL); n = sprintf(new_fmt, head_fmt , file , line , fun); strcat(new_fmt + n , fmt); va_start(ap , fmt); log4c_category_vlog(log_category , LOG4C_PRIORITY_TRACE, new_fmt , ap); va_end(ap); } int log_close() { return (log4c_fini()); }
//test-log.c
#include <stdio.h>
#include "log.h"
int main(void)
{
log_open("<span style="color: rgb(51, 51, 51); line-height: 20px;">mycat</span>");
LOG_TRACE("trace");
LOG_ERROR("error");
LOG_WARN("warn");
LOG_NOTICE("notice");
LOG_DEBUG("hello log4c!");
log_close();
return 0;
}
//配置檔案,預設名為log4crc
<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE log4c SYSTEM "">
<log4c version="1.2.1">
<config>
<bufsize>0</bufsize>
<debug level="2"/>
<nocleanup>0</nocleanup>
<reread>1</reread>
</config>
<!-- root category ========================================= -->
<category name="root" priority="notice"/>
<category name="mycat" priority="debug" appender="stdout"/>
<!-- default appenders ===================================== -->
<appender name="stdout" type="stream" layout="basic"/>
<appender name="stderr" type="stream" layout="dated"/>
<appender name="syslog" type="syslog" layout="basic"/>
<!-- default layouts ======================================= -->
<layout name="basic" type="basic"/>
<layout name="dated" type="dated"/>
</log4c>
編譯命令:
gcc test-log.c log.c -o test-log -llog4c
執行效果
./test-log
[stdout] TRACE mycat - [file:test-log.c, line:7, function:main]trace
[stdout] ERROR mycat - error
[stdout] WARN mycat - warn
[stdout] NOTICE mycat - notice
[stdout] DEBUG mycat - hello log4c!
講解:
關於log.h ,log.c封裝的內容大家可以看看,用到了可變引數巨集,可變引數這些。百度一下,就有很多人講解了。這裡就不說了。
log.h與log.c裡面用法也很簡單
log_open("category_name"); //category_name一定得是log4crc裡面已經定義的category.
關於配置檔案log4crc
配置檔案的搜尋是由LOG4C_RCPATH環境變數決定。搜尋的配置檔名為log4crc(不知道能否改變,沒研究過)
配置檔案中category的priority不知道是什麼意思,,反正好像沒什麼用。不管設定成什麼,好像都不影響。
環境變數:
LOG4C_RCPATH
holds the path to the mainlog4crc
configuration file #環境變數若未設定,則在工作目錄(一般為執行目錄)搜尋log4crc配置檔案. 如果設定了此變數,則所以用log4c庫的程式都會使用此路徑下的log4c配置檔案(可根據category區分).LOG4C_PRIORITY
holds the"root"
category priority #改變root的priority,,LOG4C_APPENDER
holds the"root"
category appender #改變root的appender,,因為root預設沒設定appender.