00001
00002
00003
00004
00005
00006
00007
00008
00009
00010 #include "LogService.hpp"
00011
00012 #if defined(PION_USE_LOG4CXX)
00013 #include <log4cxx/spi/loggingevent.h>
00014 #include <boost/lexical_cast.hpp>
00015 #elif defined(PION_USE_LOG4CPLUS)
00016 #include <log4cplus/spi/loggingevent.h>
00017 #include <boost/lexical_cast.hpp>
00018 #elif defined(PION_USE_LOG4CPP)
00019 #include <log4cpp/BasicLayout.hh>
00020 #endif
00021
00022 #include <pion/http/response_writer.hpp>
00023
00024 using namespace pion;
00025
00026 namespace pion {
00027 namespace plugins {
00028
00029
00030
00031
00032 const unsigned int LogServiceAppender::DEFAULT_MAX_EVENTS = 25;
00033
00034
00035
00036
00037 #if defined(PION_USE_LOG4CPP)
00038 LogServiceAppender::LogServiceAppender(void)
00039 : log4cpp::AppenderSkeleton("LogServiceAppender"),
00040 m_max_events(DEFAULT_MAX_EVENTS), m_num_events(0),
00041 m_layout_ptr(new log4cpp::BasicLayout())
00042 {}
00043 #else
00044 LogServiceAppender::LogServiceAppender(void)
00045 : m_max_events(DEFAULT_MAX_EVENTS), m_num_events(0)
00046 {}
00047 #endif
00048
00049
00050 #if defined(PION_USE_LOG4CXX)
00051 void LogServiceAppender::append(const log4cxx::spi::LoggingEventPtr& event)
00052 {
00053
00054 std::string formatted_string(boost::lexical_cast<std::string>(event->getTimeStamp()));
00055 formatted_string += ' ';
00056 formatted_string += event->getLevel()->toString();
00057 formatted_string += ' ';
00058 formatted_string += event->getLoggerName();
00059 formatted_string += " - ";
00060 formatted_string += event->getRenderedMessage();
00061 formatted_string += '\n';
00062 addLogString(formatted_string);
00063 }
00064 #elif defined(PION_USE_LOG4CPLUS)
00065 void LogServiceAppender::append(const log4cplus::spi::InternalLoggingEvent& event)
00066 {
00067
00068 std::string formatted_string(boost::lexical_cast<std::string>(event.getTimestamp().sec()));
00069 formatted_string += ' ';
00070 formatted_string += m_log_level_manager.toString(event.getLogLevel());
00071 formatted_string += ' ';
00072 formatted_string += event.getLoggerName();
00073 formatted_string += " - ";
00074 formatted_string += event.getMessage();
00075 formatted_string += '\n';
00076 addLogString(formatted_string);
00077 }
00078 #elif defined(PION_USE_LOG4CPP)
00079 void LogServiceAppender::_append(const log4cpp::LoggingEvent& event)
00080 {
00081 std::string formatted_string(m_layout_ptr->format(event));
00082 addLogString(formatted_string);
00083 }
00084 #endif
00085
00086 void LogServiceAppender::addLogString(const std::string& log_string)
00087 {
00088 boost::mutex::scoped_lock log_lock(m_log_mutex);
00089 m_log_events.push_back(log_string);
00090 ++m_num_events;
00091 while (m_num_events > m_max_events) {
00092 m_log_events.erase(m_log_events.begin());
00093 --m_num_events;
00094 }
00095 }
00096
00097 void LogServiceAppender::writeLogEvents(pion::http::response_writer_ptr& writer)
00098 {
00099 #if defined(PION_USE_LOG4CXX) || defined(PION_USE_LOG4CPLUS) || defined(PION_USE_LOG4CPP)
00100 boost::mutex::scoped_lock log_lock(m_log_mutex);
00101 for (std::list<std::string>::const_iterator i = m_log_events.begin();
00102 i != m_log_events.end(); ++i)
00103 {
00104 writer << *i;
00105 }
00106 #elif defined(PION_DISABLE_LOGGING)
00107 writer << "Logging is disabled." << http::types::STRING_CRLF;
00108 #else
00109 writer << "Using ostream logging." << http::types::STRING_CRLF;
00110 #endif
00111 }
00112
00113
00114
00115
00116 LogService::LogService(void)
00117 : m_log_appender_ptr(new LogServiceAppender())
00118 {
00119 #if defined(PION_USE_LOG4CXX)
00120 m_log_appender_ptr->setName("LogServiceAppender");
00121 log4cxx::Logger::getRootLogger()->addAppender(m_log_appender_ptr);
00122 #elif defined(PION_USE_LOG4CPLUS)
00123 m_log_appender_ptr->setName("LogServiceAppender");
00124 log4cplus::Logger::getRoot().addAppender(m_log_appender_ptr);
00125 #elif defined(PION_USE_LOG4CPP)
00126 log4cpp::Category::getRoot().addAppender(m_log_appender_ptr);
00127 #endif
00128 }
00129
00130 LogService::~LogService()
00131 {
00132 #if defined(PION_USE_LOG4CXX)
00133
00134 log4cxx::Logger::getRootLogger()->removeAppender(m_log_appender_ptr);
00135 #elif defined(PION_USE_LOG4CPLUS)
00136
00137 log4cplus::Logger::getRoot().removeAppender("LogServiceAppender");
00138 #elif defined(PION_USE_LOG4CPP)
00139
00140 log4cpp::Category::getRoot().removeAppender(m_log_appender_ptr);
00141 #else
00142 delete m_log_appender_ptr;
00143 #endif
00144 }
00145
00147 void LogService::operator()(http::request_ptr& http_request_ptr, tcp::connection_ptr& tcp_conn)
00148 {
00149
00150 http::response_writer_ptr writer(http::response_writer::create(tcp_conn, *http_request_ptr,
00151 boost::bind(&tcp::connection::finish, tcp_conn)));
00152 writer->get_response().set_content_type(http::types::CONTENT_TYPE_TEXT);
00153 getLogAppender().writeLogEvents(writer);
00154 writer->send();
00155 }
00156
00157
00158 }
00159 }
00160
00161
00163 extern "C" PION_PLUGIN pion::plugins::LogService *pion_create_LogService(void)
00164 {
00165 return new pion::plugins::LogService();
00166 }
00167
00169 extern "C" PION_PLUGIN void pion_destroy_LogService(pion::plugins::LogService *service_ptr)
00170 {
00171 delete service_ptr;
00172 }