我在log4cplus上写了一个包装器库。我的库有LogMessage
函数,我在其中调用log4cplus库函数来存储日志消息。
例如。 application.cpp
int main()
{
LogMessage(DEBUG_LEVEL, __FILE__, __LINE__, "This is main function");
return 0;
}
mylibrary.cpp
HRESULT
LogMessage(
__in DWORD dwLogLevel,
__in LPSTR lpszFileName,
__in DWORD dwLineNumber,
__in LPSTR lpszLogMessage
)
{
//
// Instantiating a console appender
//
SharedAppenderPtr _ConsoleAppender(new ConsoleAppender());
_ConsoleAppender->setName(LOG4CPLUS_TEXT("AppenderName"));
//
// Creating a pattern to display log events
//
log4cplus::tstring pattern = LOG4CPLUS_TEXT("%L %F %r %d{%m/%d/%y %H:%M:%S} %-5p %c - %m%n");
//
// Instantiating a layout object with PatternLayout
//
_Layout = std::auto_ptr<Layout>(new log4cplus::PatternLayout(pattern));
//
// Attaching the layout object to the appender object
//
_ConsoleAppender->setLayout(_Layout);
//
// Getting root logger and adding the Console Appender with root
// logger
//
Logger::getRoot().addAppender(_ConsoleAppender);
Logger::getRoot().setAdditivity(FALSE);
//
// Instantiating a logger
//
Logger _Logger = Logger::getInstance(LOG4CPLUS_TEXT("_Logger"));
_Logger.addAppender(_ConsoleAppender);
_Logger.setAdditivity(FALSE);
//
// Printing the log messages on the console
//
switch( dwLogLevel )
{
case DEBUG_LEVEL:
{
_Logger.log(DEBUG_LOG_LEVEL, lpszLogMessage, lpszFileName, dwLineNumber);
break;
} // DEBUG_LEVEL
case INFO_LEVEL:
{
_Logger.log(INFO_LOG_LEVEL, lpszLogMessage, lpszFileName, dwLineNumber);
break;
} // INFO_LEVEL
case WARN_LEVEL:
{
_Logger.log(WARN_LOG_LEVEL, lpszLogMessage, lpszFileName, dwLineNumber);
break;
} // WARN_LEVEL
case ERROR_LEVEL:
{
_Logger.log(ERROR_LOG_LEVEL, lpszLogMessage, lpszFileName, dwLineNumber);
break;
} // ERROR_LEVEL
case FATAL_LEVEL:
{
_Logger.log(FATAL_LOG_LEVEL, lpszLogMessage, lpszFileName, dwLineNumber);
break;
} //
default:
{
HRESULT_FROM_WIN32(ERROR_INVALID_DATA);
break;
} // default
} // switch
return hResult;
}
现在从我的应用程序中我想传递函数名称。
例如。 application.cpp
int main()
{
LogMessage(DEBUG_LEVEL, __FILE__, __LINE__, __FUNCTION__, "This is main function");
return 0;
}
如何将此日志消息打印到控制台屏幕?以下函数仅将文件和行号作为参数。我也想打印功能名称。
void log(LogLevel ll, const log4cplus::tstring& message,
const char* file=NULL, int line=-1) const;
更新 对不起,我忘了提到我已经使用PrintLogMessage #define我的LogMessage函数
#define PrintLogMessage(dwLogLevel, lpszLogMessage) \
LogMessage(dwLogLevel, _FILE, __LINE__, lpszLogMessage)
所以在应用程序中我正在使用我只需要写这一行
application.cpp
int main()
{
PrintLogMessage(DEBUG_LEVEL, "This is main function");
return 0;
}
我想写类似的
#define PrintLogMessage(dwLogLevel, lpszLogMessage) \
LogMessage(dwLogLevel, _FILE, __LINE__, __FUNCTION__, lpszLogMessage)
用于__FUNCTION__
功能。我不希望用户每次都写 FILE , LINE , FUNCTION 。
答案 0 :(得分:2)
使用Logger
类中的此功能代替:
void log (spi::InternalLoggingEvent const &) const;
提前准备InternalLoggingEvent
个实例。使用InternalLoggingEvent::setFunction()
设置事件实例的功能信息。
我已经重新阅读了您的问题以及我认为您没有按照预期方式使用log4cplus的代码。
首先,您的LogMessage
每次调用时都不应该创建appender或将追加器附加到记录器。应在应用程序开始时设置附加程序和记录程序。
看看loggingmacros.h
和那里的宏。如果使用LOG4CPLUS_ERROR
,LOG4CPLUS_INFO
等宏,则可以避免必须定义自己的宏或函数。有关如何使用这些宏的一些示例,请参阅tests/
目录。
如果您仍想避免使用log4cplus提供的宏,请查看loggingmacros.cxx
中的来源:
void
macro_forced_log (log4cplus::Logger const & logger,
log4cplus::LogLevel log_level, log4cplus::tstring const & msg,
char const * filename, int line, char const * func)
{
log4cplus::spi::InternalLoggingEvent & ev = internal::get_ptd ()->forced_log_ev;
ev.setLoggingEvent (logger.getName (), log_level, msg, filename, line);
ev.setFunction (func ? func : "");
logger.forcedLog (ev);
}
此功能由LOG4CPLUS_*()
中的各种loggingmacros.h
内部使用。它向您展示了如何填充InternalLoggingEvent
实例以及如何强制其日志。使用它作为您自己的LogMessage()
函数的示例。
您必须将forcedLog()
替换为log()
才能检查记录器阈值。
一个实现可能如下所示:
HRESULT
LogMessage(
__in DWORD dwLogLevel,
__in LPCSTR lpszFileName,
__in DWORD dwLineNumber,
__in LPCSTR lpszLogMessage,
__in LPCSTR lpszFunction)
{
log4cplus::spi::InternalLoggingEvent ev;
log4cplus::Logger logger (Logger::getRoot());
ev.setLoggingEvent (logger.getName (), dwLogLevel, lpszLogMessage, lpszFileName,
dwLineNumber);
ev.setFunction (func ? lpszFunction : "");
logger.forcedLog (ev); // or logger.log(ev)
return S_OK;
}
#define PrintLogMessage(ll, msg) \
LogMessage(ll, __FILE__, __LINE__, msg, LOG4CPLUS_MACRO_FUNCTION())
答案 1 :(得分:0)
如果您无法修改 LogMessage 功能,可以使用此方法:
int main()
{
LogMessage(DEBUG_LEVEL, __FILE__, __LINE__, "This is "__FUNCTION__" function");
// notice the missing commas ------------------------^------------^
}
由于没有逗号,编译器将连接 __ FUNCTION __ 的输出和您的消息。
修改强>
#define PrintLogMessage(dwLogLevel, lpszLogMessage) \
LogMessage(dwLogLevel, _FILE, __LINE__, __FUNCTION__ lpszLogMessage)
或
#define PrintLogMessage(dwLogLevel, lpszLogMessage) \
LogMessage(dwLogLevel, _FILE, __LINE__, lpszLogMessage __FUNCTION__)
或
#define PrintLogMessage(dwLogLevel, lpszLogMessage) \
LogMessage(dwLogLevel, _FILE, __LINE__, lpszLogMessage __FUNCTION__ "function")
或
#define PrintLogMessage(dwLogLevel, lpszLogMessage) \
LogMessage(dwLogLevel, _FILE, __LINE__, std::string(lpszLogMessage) + std::string(__FUNCTION__))