2012-01-09 46 views
5

Tôi muốn đăng nhập vào các tệp khác nhau trong mã của mình.Đăng nhập vào tệp khác với log4cxx

Làm thế nào tôi có thể làm điều đó trong Log4cxx với cấu hình xml hoặc programatically trong mã ...

  • Giả sử rằng tôi có 1.k, k + 1, .. n thành phần.
  • Họ chạy trong cùng một ứng dụng
  • Tôi muốn thành phần k log để Logger-k, k + 1 phần log để Logger-k + 1 đồng thời

Cập nhật:

Logger.addAppender() phương pháp:

log4cxx::helpers::Pool p; 

std::string paramAppender = "appxNormalAppender"; 
std::string paramFileName = "\\Logs\\MyLog.txt"; 

LOG4CXX_DECODE_CHAR(logAppender, paramAppender); 
LOG4CXX_DECODE_CHAR(logFileName, paramFileName); 


FileAppenderPtr fileAppender = 
logger->getLoggerRepository()->getRootLogger()->getAppender(logAppender); 

if(fileAppender!= NULL) 
{ 


    fileAppender->setFile(logFileName); 

    fileAppender->activateOptions(p); 

} 

này không làm việc vì

Giả sử rằng tôi đặt FileName thành Logger-k cho thành phần k, nó ghi vào Logger-k, sau đó tôi đặt tên tệp thành Logger-k + 1 cho compoent k + 1, sau đó cả hai thành phần k, và k + 1 đăng nhập cùng một tệp loggerk + 1. Có vẻ như ghi đè tên file cuối cùng hoặc ảnh hưởng tất cả những người khác ...

Tất cả compoenent compenent 1, ... compoeent k, componentk + 1, .... thành phần n trong cùng một ứng dụng ...

Trả lời

2

Tạo mỗi Logger như bình thường, và sau đó cho mỗi logger thêm một FileAppender được đặt vào tệp mong muốn thông qua phương thức Logger.addAppender().

+0

Nó không hoạt động ... Tôi đặt một cập nhật về câu hỏi của tôi ... Tôi có thể làm điều gì đó sai ... Vì vậy, tôi đặt một số mã ... – Novalis

+0

bạn đang cố gắng đặt lại tệp nhật ký cấp gốc tên và do đó mọi thứ đều ghi lại. Bạn cần thêm một FileAppender riêng biệt cho mỗi thành phần để đăng nhập vào tệp được chỉ định. – diverscuba23

+0

Có thể cung cấp mã mẫu ... Cách nhận FileAppender riêng biệt? – Novalis

1

Bạn cần tạo các ứng dụng riêng cho bạn logger. Trong ví dụ của tôi, tôi đã tạo các đối tượng afile1afile2. Tôi cũng đã tạo hai nhật ký: my.logger1my.logger2. Khi bạn sử dụng my.logger1 nó đăng nhập để mylog1 tập tin, khi bạn sử dụng my.logger2 nó đăng nhập để mylog2 tập tin.

Đây là log.properties tôi file:

log4cplus.appender.afile1.layout=log4cplus::PatternLayout 
log4cplus.appender.afile1.layout.ConversionPattern=%d [ %c{1} ] [ %-5p ] %m%n 
log4cplus.appender.afile1=log4cplus::RollingFileAppender 
log4cplus.appender.afile1.File=mylog1.log 
log4cplus.appender.afile1.MaxFileSize=5MB 
log4cplus.appender.afile1.MaxBackupIndex=2 

log4cplus.appender.afile2.layout=log4cplus::PatternLayout 
log4cplus.appender.afile2.layout.ConversionPattern=%d [ %c{1} ] [ %-5p ] %m%n 
log4cplus.appender.afile2=log4cplus::RollingFileAppender 
log4cplus.appender.afile2.File=mylog2.log 
log4cplus.appender.afile2.MaxFileSize=5MB 
log4cplus.appender.afile2.MaxBackupIndex=2 

log4cplus.logger.my.logger1=INHERIT, afile1 
log4cplus.additivity.my.logger1=false 
log4cplus.logger.my.logger2=INHERIT, afile2 
log4cplus.additivity.my.logger2=false 

Dưới đây là một ví dụ programm:
example.cpp:

#include <iostream> 
#include <log4cplus/logger.h> 
#include <log4cplus/loglevel.h> 
#include <log4cplus/configurator.h> 
#include <log4cplus/fileappender.h> 

#define MYLOG1_INFO(logEvent) LOG4CPLUS_INFO (log4cplus::Logger::getInstance("my.logger1"), logEvent) 
#define MYLOG2_INFO(logEvent) LOG4CPLUS_INFO (log4cplus::Logger::getInstance("my.logger2"), logEvent) 

int main(int argc, char**argv) 
{ 
    try 
    { 
     log4cplus::PropertyConfigurator::doConfigure("log.properties"); 
    } 
    catch(...) 
    { 
    std::cerr<<"Exception occured while opening log.properties\n"; 
    return -1; 
    } 
    MYLOG1_INFO("hello world!"); 
    MYLOG2_INFO("hello world!"); 
    return 0; 
} 

Dưới đây là Makefile (i giả log4cplus của tôi là được xây dựng trong thư mục cha mẹ):

CXXFLAGS+=-I$(abspath ../log4cplus-1.0.4/include) 
all: example.o 
    $(CXX) $^ $(abspath ../log4cplus-1.0.4/src/.libs/liblog4cplus.a) -lpthread -o test 

Hãy thử ví dụ này và bạn nên hiểu cách hoạt động của người phụ trách

Log4cplus hầu như giống như log4j.để bạn có thể đọc các nguyên tắc cơ bản log4j. Và Để có được tên lớp bạn đã truy cập log4cplus.sourceforge.net

Giới thiệu về định dạng nhật ký. Tài liệu cho log4cplus chỉ có sẵn trong doxygen. vì vậy đây bạn có thể đọc về formating in pattern layout
Và nếu bạn muốn đăng nhập quá trình id, hơn bạn nên sử dụng% i trong mô hình chuyển đổi bố trí của bạn
dụ:

... 
log4cplus.appender.afile2.layout.ConversionPattern=[%i] %m%n 
... 

Nó sẽ đăng nhập id quá trình và thông điệp

+0

xin lỗi, đã viết về log4cplus. Nhưng hãy tin tôi, nó tốt hơn log4cxx – 2r2w

+0

Có vẻ như log4cplus là "Dead". [Tháng 1 năm 2011 phát hành cuối cùng] và nó cũng bị thiếu documenttaion. Tôi có thể chọn log4cplus nếu tôi có thể làm với điều này: Kiểm tra câu hỏi của tôi: http://stackoverflow.com/questions/9082413/add-process-id-to-log-file-name-in-log4cxx – Novalis

+0

bản phát hành mới nhất của log4cxx là trong 2008-04-03 http://logging.apache.org/log4cxx/changes-report.html và realease mới nhất của log4cplus là vào năm 2011. Log4cxx khác có phiên bản 0.10 và log4cplus có phiên bản 1.04 Vì vậy, có vẻ như log4cxx là dự án chết nhiều hơn – 2r2w

1

Đối với các thành phần năng động thử điều này:

#include <boost/foreach.hpp> 
#include <boost/thread.hpp> 
#include <boost/bind.hpp> 
#include <boost/lexical_cast.hpp> 

#include <log4cxx/Logger.h> 
#include <log4cxx/LogManager.h> 
#include <log4cxx/xml/domconfigurator.h> 
#include <log4cxx/FileAppender.h> 
#include <log4cxx/SimpleLayout.h> 
#include <log4cxx/helpers/transcoder.h> 


void func(int k) { 
    std::string strName = "Log." + boost::lexical_cast<std::string>(k); 
    log4cxx::LoggerPtr log = log4cxx::Logger::getLogger(strName); 
    LOG4CXX_DECODE_CHAR(fileName, strName + ".log"); 
    log4cxx::FileAppenderPtr appender(new log4cxx::FileAppender(new log4cxx::SimpleLayout, fileName, false)); 
    log->addAppender(appender); 

    LOG4CXX_INFO(log, strName); 

    log->removeAppender(appender); 
} 

int main(int argc, char * argv[]) { 
    log4cxx::xml::DOMConfigurator::configure("trace.xml"); 
    if(log4cxx::Logger::getLogger("Log")->getAllAppenders().empty()) { 
     std::cout << "failed to config log4cxx" << std::endl; 
     return 1; 
    } 
    log4cxx::LoggerPtr log = log4cxx::Logger::getLogger("Log"); 

    boost::thread_group threadGroup; 
    for(int k = 0; k != 3; ++k) { 
     threadGroup.create_thread(boost::bind(func, k)); 
    } 
    threadGroup.join_all(); 
    return 0; 
} 

với đơn giản trace.xml

<?xml version="1.0" encoding="UTF-8" ?> 
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/"> 
    <appender name="ConsoleAppender" class="org.apache.log4j.ConsoleAppender"> 
     <param name="Target" value="System.out"/> 
     <layout class="org.apache.log4j.SimpleLayout"/> 
    </appender> 

    <root> 
     <level value="all"/> 
    </root> 

    <category name="Log"> 
     <level value="INFO"/> 
     <appender-ref ref="ConsoleAppender"/> 
    </category> 
</log4j:configuration> 
Các vấn đề liên quan