test

#define CFA_INFRA_LOG_SOURCE 1
#include <CFAInfra/logging/Logging.hpp>
#include <iostream>

#pragma warning( disable : 4231 )

#include <log4cxx/logger.h>
#include <log4cxx/logmanager.h>
#include <log4cxx/basicconfigurator.h>

#ifdef _DEBUG
# pragma comment(lib, "Project_log4cxx_MSVC2005_Debug.lib")
#else
# pragma comment(lib, "Project_log4cxx_MSVC2005_Release.lib")
#endif

namespace cfa { namespace log
{
struct ILog4CxxLogSource : public ILogSource
{
virtual log4cxx::LoggerPtr logger() const = 0;
};

class Log4CxxLogSource : public ILog4CxxLogSource
{
public:
Log4CxxLogSource(const std::string& name)
{
logger_ = log4cxx::Logger::getLogger(name);
}

virtual log4cxx::LoggerPtr logger() const
{
return logger_;
}

private:
log4cxx::LoggerPtr logger_;
};

shared_ptr<ILogSource> MakeLogSource(const std::string& name)
{
return make_shared_ptr(new Log4CxxLogSource(name));
}

namespace
{
Log4CxxLogSource defaultSource("DEFAULT");
shared_ptr<Logger> defaultLogger;
}

Logger& Logger::Default()
{
if (!defaultLogger)
{
log4cxx::spi::LoggerRepositoryPtr repository = log4cxx::LogManager::getLoggerRepository();
if (!repository->isConfigured() || !repository->getRootLogger())
{
log4cxx::BasicConfigurator::configure();
}
else if (log4cxx::LoggerPtr rootLogger = repository->getRootLogger())
{
log4cxx::AppenderList rootAppenders = rootLogger->getAllAppenders();
if (rootAppenders.empty())
{
log4cxx::BasicConfigurator::configure();
}
}
defaultLogger = make_shared_ptr(new Logger);
}
return *defaultLogger;
}

void Logger::Log(LogLevel level, const ILogRecord& logRecord, const ILogSource& source)
{
const ILog4CxxLogSource* logger = dynamic_cast<const ILog4CxxLogSource*>(&source);
if (!logger)
logger = &defaultSource;

if (level == Spam)
{
LOG4CXX_TRACE(logger->logger(), source << logRecord);
}
else if (level == Trace)
{
LOG4CXX_TRACE(logger->logger(), source << logRecord);
}
else if (level == Debug)
{
LOG4CXX_DEBUG(logger->logger(), source << logRecord);
}
else if (level == Info)
{
LOG4CXX_INFO(logger->logger(), source << logRecord);
}
else if (level == Warning)
{
LOG4CXX_WARN (logger->logger(), source << logRecord);
}
else if (level == Error)
{
LOG4CXX_ERROR(logger->logger(), source << logRecord);
}
else if (level == Critical)
{
LOG4CXX_FATAL(logger->logger(), source << logRecord);
}
}

shared_ptr<ILogRecepient> GetDefaultConsoleLogRecepient()
{
return null_ptr;
}

void Logger::SetLogLevel(shared_ptr<ILogRecepient> logRecepient, LogLevel logLevel)
{
log4cxx::spi::LoggerRepositoryPtr repository = log4cxx::LogManager::getLoggerRepository();
log4cxx::LoggerPtr rootLogger = repository->getRootLogger();
if (logLevel == Spam)
rootLogger->setLevel(log4cxx::Level::getTrace());
else if (logLevel == Trace)
rootLogger->setLevel(log4cxx::Level::getTrace());
else if (logLevel == Debug)
rootLogger->setLevel(log4cxx::Level::getDebug());
else if (logLevel == Info)
rootLogger->setLevel(log4cxx::Level::getInfo());
else if (logLevel == Warning)
rootLogger->setLevel(log4cxx::Level::getWarn());
else if (logLevel == Error)
rootLogger->setLevel(log4cxx::Level::getError());
else if (logLevel == Critical)
rootLogger->setLevel(log4cxx::Level::getFatal());
}

} } // cfa::log

#ifndef __CFA_INFRA_LOGGING_HEADER__
#define __CFA_INFRA_LOGGING_HEADER__

#include <CFAInfra/CFAInfra.hpp>
#include <iostream>

namespace cfa { namespace log
{
struct ILogSource
{
virtual ~ILogSource() {}
virtual void Print(std::ostream& os) const {}
friend std::ostream& operator << (std::ostream& os, const ILogSource& src)
{
src.Print(os);
return os;
}
};

CFAINFRA_API shared_ptr<ILogSource> MakeLogSource(const std::string& name);

class DefaultLogSource : public ILogSource
{
public:
DefaultLogSource(const char* filename, unsigned int lineNumber)
: filename_(filename)
, lineNumber_(lineNumber)
{
}

virtual void Print(std::ostream& os) const
{
os << "[" << filename_ << "/line:" << lineNumber_ << "] " ;
}

private:
const char* filename_;
unsigned int lineNumber_;
};

struct ILogRecord
{
virtual void Print(std::ostream& os) const = 0;
friend std::ostream& operator << (std::ostream& os, const ILogRecord& lr)
{
lr.Print(os);
return os;
}
};

struct CFAINFRA_API ILogRecepient
{
virtual ~ILogRecepient() {}
};

CFAINFRA_API shared_ptr<ILogRecepient> GetDefaultConsoleLogRecepient();

class CFAINFRA_API Logger
{
public:
static Logger& Default();
enum LogLevel
{
Spam = 0,
Trace = 1,
Debug = 2,
Info = 3,
Warning = 4,
Error = 5,
Critical = 6
};
void Log(LogLevel level, const ILogRecord& logRecord, const ILogSource& source);
void Log(LogLevel level, const ILogRecord& logRecord, const shared_ptr<ILogSource>& source)
{
Log(level, logRecord, *source);
}
void Log(LogLevel level, const ILogRecord& logRecord, ILogSource* source)
{
Log(level, logRecord, *source);
}

void SetLogLevel(shared_ptr<ILogRecepient> logRecepient, Logger::LogLevel logLevel);
};

namespace detail
{
template<class ParentT, class ValueT>
class LogRecord;

class BaseLogRecord
{
public:
void Print(std::ostream& os) const
{
}

template<class T>
LogRecord<T, BaseLogRecord> operator << (const T& rhs) const
{
return LogRecord<T, BaseLogRecord>(rhs, *this);
}
};

template<class ValueT, class ParentT>
class LogRecord
{
public:
LogRecord(const ValueT& value, const ParentT& parent)
: parent_(parent)
, value_(value)
{
}

template<class T>
LogRecord<T, LogRecord<ValueT, ParentT> > operator << (const T& rhs) const
{
return LogRecord<T, LogRecord<ValueT, ParentT> >(rhs, *this);
}

void Print(std::ostream& os) const
{
parent_.Print(os);
os << value_;
}
private:
const ParentT& parent_;
const ValueT& value_;
};

template<class LogRecordT>
class LogRecordWrapper : public ILogRecord
{
public:
LogRecordWrapper(const LogRecordT& logRecord)
: logRecord_(logRecord)
{
}
virtual void Print(std::ostream& os) const
{
logRecord_.Print(os);
}
private:
const LogRecordT& logRecord_;
};

template<class LogRecordT>
LogRecordWrapper<LogRecordT> MakeLogRecordWrapper(const LogRecordT& logRecord)
{
return LogRecordWrapper<LogRecordT>(logRecord);
}
} // detail

} } // cfa::log

#define CFA_LOG(source, level, message) \
cfa::log::Logger::Default().Log( \
level, \
cfa::log::detail::MakeLogRecordWrapper(cfa::log::detail::BaseLogRecord() << message), \
source \
) \

#define CFA_DEFAULT_LOG_SOURCE cfa::log::DefaultLogSource(__FILE__, __LINE__)
#define CFA_LOG_SPAM(source, message) CFA_LOG(source, cfa::log::Logger::Spam, message)
#define CFA_LOG_TRACE(source, message) CFA_LOG(source, cfa::log::Logger::Trace, message)
#define CFA_LOG_DEBUG(source, message) CFA_LOG(source, cfa::log::Logger::Debug, message)
#define CFA_LOG_INFO(source, message) CFA_LOG(source, cfa::log::Logger::Info, message)
#define CFA_LOG_WARNING(source, message) CFA_LOG(source, cfa::log::Logger::Warning, message)
#define CFA_LOG_ERROR(source, message) CFA_LOG(source, cfa::log::Logger::Error, message)
#define CFA_LOG_CRITICAL(source, message) CFA_LOG(source, cfa::log::Logger::Critical, message)

/// Use our CFA_LOG macros instead of the log4cxx ones
#ifdef LOG4CXX_INFO
#ifndef CFA_INFRA_LOG_SOURCE
# undef LOG4CXX_INFO
# undef LOG4CXX_DEBUG
# undef LOG4CXX_ERROR
#endif
#endif

#endif // __CFA_INFRA_LOGGING_HEADER__
Last edited on
What's the question? Also use code tags. See http://www.cplusplus.com/forum/beginner/1/ .
Topic archived. No new replies allowed.