log4cpp安装使用

1. 主页:http://log4cpp.sourceforge.net
“Log4cpp is library of C++ classes for flexible logging to files, syslog, IDSA and other destinations. It is modeled after the Log4j Java library, staying as close to their API as is reasonable.”

api文档地址:http://log4cpp.sourceforge.net/api/hierarchy.html

 

2.下载安装
环境:ubuntu 14.04 LTS,gcc 4.8.4

下载源码包 log4cpp-1.1.2rc1.tar.gz
$tar xzvf log4cpp-1.1.2rc1.tar.gz
$cd log4cpp
$./configure --with-pthreads
$make
$make check
$make install

安装完成后,头文件在/usr/local/include/log4cpp,库安装在/usr/local/lib/,文件名liglog4cpp.so.5.0.6,还有几个符号链接

 

3.测试
测试代码 main.cpp

#include "log4cpp/Category.hh"
#include "log4cpp/PropertyConfigurator.hh"

int main(int argc, char* argv[])
{
    std::string initFileName = "log4cpp.properties";
    log4cpp::PropertyConfigurator::configure(initFileName);

    log4cpp::Category& root = log4cpp::Category::getRoot();

    log4cpp::Category& sub1 = 
        log4cpp::Category::getInstance(std::string("sub1"));

    log4cpp::Category& sub2 = 
        log4cpp::Category::getInstance(std::string("sub1.sub2"));

    root.warn("Storm is coming");

    sub1.debug("Received storm warning");
    sub1.info("Closing all hatches");

    sub2.debug("Hiding solar panels");
    sub2.error("Solar panels are blocked");
    sub2.debug("Applying protective shield");
    sub2.warn("Unfolding protective shield");
    sub2.info("Solar panels are shielded");

    sub1.info("All hatches closed");

    root.info("Ready for storm.");

    log4cpp::Category::shutdown();

    return 0;
}
main.cpp

编译:g++ main.cpp -L/usr/local/lib -llog4cpp -pthread -I/usr/local/include -o main

log配置文件:log4cpp.properties

log4cpp.rootCategory=DEBUG, rootAppender
log4cpp.category.sub1=DEBUG, A1, A2
log4cpp.category.sub1.sub2=DEBUG, A3

log4cpp.appender.rootAppender=ConsoleAppender
log4cpp.appender.rootAppender.layout=PatternLayout
log4cpp.appender.rootAppender.layout.ConversionPattern=%d [%p] %m%n 

log4cpp.appender.A1=FileAppender
log4cpp.appender.A1.fileName=A1.log
log4cpp.appender.A1.layout=BasicLayout

log4cpp.appender.A2=FileAppender
log4cpp.appender.A2.threshold=WARN
log4cpp.appender.A2.fileName=A2.log
log4cpp.appender.A2.layout=PatternLayout
log4cpp.appender.A2.layout.ConversionPattern=%d [%p] %m%n 

log4cpp.appender.A3=RollingFileAppender
log4cpp.appender.A3.fileName=A3.log
log4cpp.appender.A3.maxFileSize=200
log4cpp.appender.A3.maxBackupIndex=1
log4cpp.appender.A3.layout=PatternLayout
log4cpp.appender.A3.layout.ConversionPattern=%d [%p] %m%n
View Code

 

4.简单封装

Log.h

#ifndef LOG_H
#define LOG_H

#include <log4cpp/Category.hh>
#include <log4cpp/PropertyConfigurator.hh>
#include <log4cpp/Priority.hh>

#include <stdarg.h>
#include <syslog.h>

// confirm to log4cpp::priority::PriorityLevel
#define DEBUG_LEVEL  700
#define INFO_LEVEL   600
#define WARN_LEVEL   400
#define ERROR_LEVEL  300
#define FATAL_LEVEL  0

#define LOG(level,format, args...) do {\
        Log::getInstance().write(level, __FUNCTION__, format, ##args);\
    }while(0);

class Log
{
    public:
        static Log& getInstance() { return instance_;}
        void write(int level, const char* func, const char* format, ...);

    private:
        Log();
        virtual ~Log();

        void init();
        void cleanup();

        log4cpp::Priority::Value currentPriority();
        void formatFunc(const char* func, const char* format, va_list alist, std::string& msg);

    private:
        static Log instance_;
        log4cpp::Category* logger_;
};

#endif // LOG_H
Log.h

Log.cpp

#include "Log.h"

#include <syslog.h>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <pthread.h>
#include <sys/timeb.h>
#include <time.h>
#include <errno.h>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <stdexcept>
#include <log4cpp/Configurator.hh>

using std::string;

#define BUF_LEN 4096

//int fdLog_ = -1;
Log Log::instance_;

Log::Log()
{
    syslog(LOG_INFO, "Log constructor");
    init();
}

Log::~Log()
{
    syslog(LOG_INFO, "Log deconstructor");
    cleanup();
}

void Log::init()
{
    logger_ = NULL;

    try {
        std::string basePath("/myapp/lib/");
        std::string confFile = basePath + "log4cpp.priority";

        log4cpp::PropertyConfigurator::configure(confFile);
        log4cpp::Category& root = log4cpp::Category::getRoot();

        log4cpp::Category& sub1 =
            log4cpp::Category::getInstance(std::string("sub1"));

        logger_ = &sub1;
    } catch(std::exception const& e) {
        syslog(LOG_NOTICE, "init log error[%s]", e.what());
    } catch(...) {
        syslog(LOG_INFO, "init log error[%d, %s]", errno, strerror(errno));
    }

    syslog(LOG_INFO, "log init finished");
}

void Log::cleanup()
{
    log4cpp::Category::shutdown();
}

int Log::currentPriority()
{
    if (logger_) {
        return logger_->getPriority();
    }

    return INFO_LEVEL;
}

void Log::write(int level, const char* func, const char* format, ...)
{
    if (Config::getInstance().NoLogOutput_) {
        return;
    }
    if (level > currentPriority()) {
        return;
    }
    if (NULL == logger_) {
        return;
    }

    std::string info;
    va_list alist;
    va_start (alist, format);
    formatFunc(func, format, alist, info);
    va_end(alist);

    try {
        switch(level) {
        case FATAL_LEVEL:
            logger_->fatal(info);
            break;
        case ERROR_LEVEL:
            logger_->error(info);
            break;
        case WARN_LEVEL:
            logger_->warn(info);
            break;
        case INFO_LEVEL:
            logger_->info(info);
            break;
        case DEBUG_LEVEL:
            logger_->debug(info);
            break;
        default:
            break;
        }
    } catch(...) {
        syslog(LOG_INFO, "output log failed");
    }
}

void Log::formatFunc(const char* func, const char* format, va_list alist, std::string& msg)
{
    char buf[BUF_LEN] = {0};

    int prefixLen = snprintf(buf, BUF_LEN-1, " 0x%lX %s(): ",\
        pthread_self(), func);

    int contentLen = vsnprintf(buf+prefixLen, BUF_LEN-1-prefixLen, format, alist);

    int dataLen = prefixLen + contentLen;
    buf[dataLen] = '\n';

    msg = buf;
}
#endif
Log.cpp

 

posted @ 2016-01-11 18:42  onemuji  阅读(4381)  评论(0编辑  收藏  举报