From 165711162160837388b2e507aa95d46a0c5529d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Luis=20=C3=81ngel=20San=20Mart=C3=ADn?= Date: Thu, 16 Jun 2016 22:16:01 +0200 Subject: [PATCH] Updated loggin component of QtWebApp to version 1.6.5 --- .../server/lib/logging/dualfilelogger.cpp | 14 ++-- .../server/lib/logging/dualfilelogger.h | 22 ++++-- .../server/lib/logging/filelogger.cpp | 69 ++++++++++++------- .../server/lib/logging/filelogger.h | 3 +- .../server/lib/logging/logger.cpp | 61 ++++++++++------ YACReaderLibrary/server/lib/logging/logger.h | 13 ++-- .../server/lib/logging/logging.pri | 5 +- .../server/lib/logging/logmessage.cpp | 52 ++++++++------ .../server/lib/logging/logmessage.h | 14 ++-- 9 files changed, 162 insertions(+), 91 deletions(-) diff --git a/YACReaderLibrary/server/lib/logging/dualfilelogger.cpp b/YACReaderLibrary/server/lib/logging/dualfilelogger.cpp index 7329cae0..80738e9d 100644 --- a/YACReaderLibrary/server/lib/logging/dualfilelogger.cpp +++ b/YACReaderLibrary/server/lib/logging/dualfilelogger.cpp @@ -13,8 +13,14 @@ DualFileLogger::DualFileLogger(QSettings* firstSettings, QSettings* secondSettin secondLogger=new FileLogger(secondSettings, refreshInterval, this); } - -void DualFileLogger::log(const QtMsgType type, const QString& message) { - firstLogger->log(type, message); - secondLogger->log(type, message); +void DualFileLogger::log(const QtMsgType type, const QString& message, const QString &file, const QString &function, const int line) +{ + firstLogger->log(type,message,file,function,line); + secondLogger->log(type,message,file,function,line); +} + +void DualFileLogger::clear(const bool buffer, const bool variables) +{ + firstLogger->clear(buffer,variables); + secondLogger->clear(buffer,variables); } diff --git a/YACReaderLibrary/server/lib/logging/dualfilelogger.h b/YACReaderLibrary/server/lib/logging/dualfilelogger.h index 39bec859..e65236a0 100644 --- a/YACReaderLibrary/server/lib/logging/dualfilelogger.h +++ b/YACReaderLibrary/server/lib/logging/dualfilelogger.h @@ -6,11 +6,12 @@ #ifndef DUALFILELOGGER_H #define DUALFILELOGGER_H -#include "logger.h" -#include "filelogger.h" #include #include #include +#include "logglobal.h" +#include "logger.h" +#include "filelogger.h" /** Logs messages into two log files simultaneously. @@ -18,7 +19,7 @@ @see FileLogger for a description of the two underlying loggers. */ -class DualFileLogger : public Logger { +class DECLSPEC DualFileLogger : public Logger { Q_OBJECT Q_DISABLE_COPY(DualFileLogger) public: @@ -37,13 +38,24 @@ public: DualFileLogger(QSettings* firstSettings, QSettings* secondSettings, const int refreshInterval=10000, QObject *parent = 0); /** - Decorate and log a message. + Decorate and log the message, if type>=minLevel. This method is thread safe. @param type Message type (level) @param message Message text + @param file Name of the source file where the message was generated (usually filled with the macro __FILE__) + @param function Name of the function where the message was generated (usually filled with the macro __LINE__) + @param line Line Number of the source file, where the message was generated (usually filles with the macro __func__ or __FUNCTION__) @see LogMessage for a description of the message decoration. */ - virtual void log(const QtMsgType type, const QString& message); + virtual void log(const QtMsgType type, const QString& message, const QString &file="", const QString &function="", const int line=0); + + /** + Clear the thread-local data of the current thread. + This method is thread safe. + @param buffer Whether to clear the backtrace buffer + @param variables Whether to clear the log variables + */ + virtual void clear(const bool buffer=true, const bool variables=true); private: diff --git a/YACReaderLibrary/server/lib/logging/filelogger.cpp b/YACReaderLibrary/server/lib/logging/filelogger.cpp index 06cf122d..f12b29be 100644 --- a/YACReaderLibrary/server/lib/logging/filelogger.cpp +++ b/YACReaderLibrary/server/lib/logging/filelogger.cpp @@ -15,7 +15,8 @@ #include #include "yacreader_global.h" -void FileLogger::refreshSettings() { +void FileLogger::refreshSettings() +{ mutex.lock(); // Save old file name for later comparision with new settings QString oldFileName=fileName; @@ -41,7 +42,8 @@ void FileLogger::refreshSettings() { bufferSize=settings->value("bufferSize",0).toInt(); // Create new file if the filename has been changed - if (oldFileName!=fileName) { + if (oldFileName!=fileName) + { fprintf(stderr,"Logging to %s\n",qPrintable(fileName)); close(); open(); @@ -57,7 +59,8 @@ FileLogger::FileLogger(QSettings* settings, const int refreshInterval, QObject* Q_ASSERT(refreshInterval>=0); this->settings=settings; file=0; - if (refreshInterval>0) { + if (refreshInterval>0) + { refreshTimer.start(refreshInterval,this); } flushTimer.start(1000,this); @@ -65,26 +68,31 @@ FileLogger::FileLogger(QSettings* settings, const int refreshInterval, QObject* } -FileLogger::~FileLogger() { +FileLogger::~FileLogger() +{ close(); } -void FileLogger::write(const LogMessage* logMessage) { +void FileLogger::write(const LogMessage* logMessage) +{ // Try to write to the file - if (file) { + if (file) + { // Write the message file->write(qPrintable(logMessage->toString(msgFormat,timestampFormat))); // Flush error messages immediately, to ensure that no important message // gets lost when the program terinates abnormally. - if (logMessage->getType()>=QtCriticalMsg) { + if (logMessage->getType()>=QtCriticalMsg) + { file->flush(); } // Check for success - if (file->error()) { + if (file->error()) + { close(); qWarning("Cannot write to log file %s: %s",qPrintable(fileName),qPrintable(file->errorString())); } @@ -92,19 +100,23 @@ void FileLogger::write(const LogMessage* logMessage) { } // Fall-back to the super class method, if writing failed - if (!file) { + if (!file) + { Logger::write(logMessage); } } -void FileLogger::open() { - if (fileName.isEmpty()) { +void FileLogger::open() +{ + if (fileName.isEmpty()) + { qWarning("Name of logFile is empty"); } else { file=new QFile(fileName); - if (!file->open(QIODevice::WriteOnly | QIODevice::Append | QIODevice::Text)) { + if (!file->open(QIODevice::WriteOnly | QIODevice::Append | QIODevice::Text)) + { qWarning("Cannot open log file %s: %s",qPrintable(fileName),qPrintable(file->errorString())); file=0; } @@ -112,8 +124,10 @@ void FileLogger::open() { } -void FileLogger::close() { - if (file) { +void FileLogger::close() +{ + if (file) + { file->close(); delete file; file=0; @@ -123,18 +137,22 @@ void FileLogger::close() { void FileLogger::rotate() { // count current number of existing backup files int count=0; - forever { + forever + { QFile bakFile(QString("%1.%2").arg(fileName).arg(count+1)); - if (bakFile.exists()) { + if (bakFile.exists()) + { ++count; } - else { + else + { break; } } // Remove all old backup files that exceed the maximum number - while (maxBackups>0 && count>=maxBackups) { + while (maxBackups>0 && count>=maxBackups) + { QFile::remove(QString("%1.%2").arg(fileName).arg(count)); --count; } @@ -149,21 +167,26 @@ void FileLogger::rotate() { } -void FileLogger::timerEvent(QTimerEvent* event) { - if (!event) { +void FileLogger::timerEvent(QTimerEvent* event) +{ + if (!event) + { return; } - else if (event->timerId()==refreshTimer.timerId()) { + else if (event->timerId()==refreshTimer.timerId()) + { refreshSettings(); } - else if (event->timerId()==flushTimer.timerId() && file) { + else if (event->timerId()==flushTimer.timerId() && file) + { mutex.lock(); // Flush the I/O buffer file->flush(); // Rotate the file if it is too large - if (maxSize>0 && file->size()>=maxSize) { + if (maxSize>0 && file->size()>=maxSize) + { close(); rotate(); open(); diff --git a/YACReaderLibrary/server/lib/logging/filelogger.h b/YACReaderLibrary/server/lib/logging/filelogger.h index 617b5bff..71b840db 100644 --- a/YACReaderLibrary/server/lib/logging/filelogger.h +++ b/YACReaderLibrary/server/lib/logging/filelogger.h @@ -11,6 +11,7 @@ #include #include #include +#include "logglobal.h" #include "logger.h" /** @@ -45,7 +46,7 @@ @see Logger for a descrition of the buffer. */ -class FileLogger : public Logger { +class DECLSPEC FileLogger : public Logger { Q_OBJECT Q_DISABLE_COPY(FileLogger) public: diff --git a/YACReaderLibrary/server/lib/logging/logger.cpp b/YACReaderLibrary/server/lib/logging/logger.cpp index de3ab1a5..f2d17d2a 100644 --- a/YACReaderLibrary/server/lib/logging/logger.cpp +++ b/YACReaderLibrary/server/lib/logging/logger.cpp @@ -9,6 +9,7 @@ #include #include #include +#include Logger* Logger::defaultLogger=0; @@ -16,9 +17,6 @@ Logger* Logger::defaultLogger=0; QThreadStorage*> Logger::logVars; -QThreadStorage*> Logger::buffers; - - QMutex Logger::mutex; @@ -32,7 +30,8 @@ Logger::Logger(QObject* parent) Logger::Logger(const QString msgFormat, const QString timestampFormat, const QtMsgType minLevel, const int bufferSize, QObject* parent) - :QObject(parent) { + :QObject(parent) +{ this->msgFormat=msgFormat; this->timestampFormat=timestampFormat; this->minLevel=minLevel; @@ -40,7 +39,8 @@ Logger::Logger(const QString msgFormat, const QString timestampFormat, const QtM } -void Logger::msgHandler(const QtMsgType type, const QString &message, const QString &file, const QString &function, const int line) { +void Logger::msgHandler(const QtMsgType type, const QString &message, const QString &file, const QString &function, const int line) +{ static QMutex recursiveMutex(QMutex::Recursive); static QMutex nonRecursiveMutex(QMutex::NonRecursive); @@ -50,11 +50,13 @@ void Logger::msgHandler(const QtMsgType type, const QString &message, const QStr recursiveMutex.lock(); // Fall back to stderr when this method has been called recursively. - if (defaultLogger && nonRecursiveMutex.tryLock()) { + if (defaultLogger && nonRecursiveMutex.tryLock()) + { defaultLogger->log(type, message, file, function, line); nonRecursiveMutex.unlock(); } - else { + else + { fputs(qPrintable(message),stderr); fflush(stderr); } @@ -69,19 +71,23 @@ void Logger::msgHandler(const QtMsgType type, const QString &message, const QStr #if QT_VERSION >= 0x050000 - void Logger::msgHandler5(const QtMsgType type, const QMessageLogContext &context, const QString &message) { + void Logger::msgHandler5(const QtMsgType type, const QMessageLogContext &context, const QString &message) + { (void)(context); // suppress "unused parameter" warning msgHandler(type,message,context.file,context.function,context.line); } #else - void Logger::msgHandler4(const QtMsgType type, const char* message) { + void Logger::msgHandler4(const QtMsgType type, const char* message) + { msgHandler(type,message); } #endif -Logger::~Logger() { - if (defaultLogger==this) { +Logger::~Logger() +{ + if (defaultLogger==this) + { #if QT_VERSION >= 0x050000 qInstallMessageHandler(0); #else @@ -92,13 +98,15 @@ Logger::~Logger() { } -void Logger::write(const LogMessage* logMessage) { +void Logger::write(const LogMessage* logMessage) +{ fputs(qPrintable(logMessage->toString(msgFormat,timestampFormat)),stderr); fflush(stderr); } -void Logger::installMsgHandler() { +void Logger::installMsgHandler() +{ defaultLogger=this; #if QT_VERSION >= 0x050000 qInstallMessageHandler(msgHandler5); @@ -108,9 +116,11 @@ void Logger::installMsgHandler() { } -void Logger::set(const QString& name, const QString& value) { +void Logger::set(const QString& name, const QString& value) +{ mutex.lock(); - if (!logVars.hasLocalData()) { + if (!logVars.hasLocalData()) + { logVars.setLocalData(new QHash); } logVars.localData()->insert(name,value); @@ -118,23 +128,27 @@ void Logger::set(const QString& name, const QString& value) { } -void Logger::clear(const bool buffer, const bool variables) { +void Logger::clear(const bool buffer, const bool variables) +{ mutex.lock(); - if (buffer && buffers.hasLocalData()) { + if (buffer && buffers.hasLocalData()) + { QList* buffer=buffers.localData(); while (buffer && !buffer->isEmpty()) { LogMessage* logMessage=buffer->takeLast(); delete logMessage; } } - if (variables && logVars.hasLocalData()) { + if (variables && logVars.hasLocalData()) + { logVars.localData()->clear(); } mutex.unlock(); } -void Logger::log(const QtMsgType type, const QString& message, const QString &file, const QString &function, const int line) { +void Logger::log(const QtMsgType type, const QString& message, const QString &file, const QString &function, const int line) +{ mutex.lock(); // If the buffer is enabled, write the message into it @@ -148,12 +162,14 @@ void Logger::log(const QtMsgType type, const QString& message, const QString &fi LogMessage* logMessage=new LogMessage(type,message,logVars.localData(),file,function,line); buffer->append(logMessage); // Delete oldest message if the buffer became too large - if (buffer->size()>bufferSize) { + if (buffer->size()>bufferSize) + { delete buffer->takeFirst(); } // If the type of the message is high enough, print the whole buffer if (type>=minLevel) { - while (!buffer->isEmpty()) { + while (!buffer->isEmpty()) + { LogMessage* logMessage=buffer->takeFirst(); write(logMessage); delete logMessage; @@ -163,7 +179,8 @@ void Logger::log(const QtMsgType type, const QString& message, const QString &fi // Buffer is disabled, print the message if the type is high enough else { - if (type>=minLevel) { + if (type>=minLevel) + { LogMessage logMessage(type,message,logVars.localData(),file,function,line); write(&logMessage); } diff --git a/YACReaderLibrary/server/lib/logging/logger.h b/YACReaderLibrary/server/lib/logging/logger.h index adcedfd3..0ced8051 100644 --- a/YACReaderLibrary/server/lib/logging/logger.h +++ b/YACReaderLibrary/server/lib/logging/logger.h @@ -6,13 +6,13 @@ #ifndef LOGGER_H #define LOGGER_H -#include - #include #include #include #include #include +#include +#include "logglobal.h" #include "logmessage.h" /** @@ -45,7 +45,7 @@ because logging to the console is less useful. */ -class Logger : public QObject { +class DECLSPEC Logger : public QObject { Q_OBJECT Q_DISABLE_COPY(Logger) public: @@ -100,10 +100,11 @@ public: /** Clear the thread-local data of the current thread. + This method is thread safe. @param buffer Whether to clear the backtrace buffer @param variables Whether to clear the log variables */ - static void clear(const bool buffer=true, const bool variables=true); + virtual void clear(const bool buffer=true, const bool variables=true); protected: @@ -119,7 +120,7 @@ protected: /** Size of backtrace buffer, number of messages per thread. 0=disabled */ int bufferSize; - /** Used to synchronize access to the static members */ + /** Used to synchronize access of concurrent threads */ static QMutex mutex; /** @@ -176,7 +177,7 @@ private: static QThreadStorage*> logVars; /** Thread local backtrace buffers */ - static QThreadStorage*> buffers; + QThreadStorage*> buffers; }; diff --git a/YACReaderLibrary/server/lib/logging/logging.pri b/YACReaderLibrary/server/lib/logging/logging.pri index 17eae35e..13c296c7 100644 --- a/YACReaderLibrary/server/lib/logging/logging.pri +++ b/YACReaderLibrary/server/lib/logging/logging.pri @@ -1,5 +1,6 @@ INCLUDEPATH += $$PWD DEPENDPATH += $$PWD -HEADERS += $$PWD/logmessage.h $$PWD/logger.h $$PWD/filelogger.h $$PWD/dualfilelogger.h -SOURCES += $$PWD/logmessage.cpp $$PWD/logger.cpp $$PWD/filelogger.cpp $$PWD/dualfilelogger.cpp +HEADERS += $$PWD/logglobal.h $$PWD/logmessage.h $$PWD/logger.h $$PWD/filelogger.h $$PWD/dualfilelogger.h + +SOURCES += $$PWD/logmessage.cpp $$PWD/logger.cpp $$PWD/filelogger.cpp $$PWD/dualfilelogger.cpp diff --git a/YACReaderLibrary/server/lib/logging/logmessage.cpp b/YACReaderLibrary/server/lib/logging/logmessage.cpp index 4d610383..ef359302 100644 --- a/YACReaderLibrary/server/lib/logging/logmessage.cpp +++ b/YACReaderLibrary/server/lib/logging/logmessage.cpp @@ -6,7 +6,8 @@ #include "logmessage.h" #include -LogMessage::LogMessage(const QtMsgType type, const QString& message, QHash* logVars, const QString &file, const QString &function, const int line) { +LogMessage::LogMessage(const QtMsgType type, const QString& message, QHash* logVars, const QString &file, const QString &function, const int line) +{ this->type=type; this->message=message; this->file=file; @@ -17,16 +18,19 @@ LogMessage::LogMessage(const QtMsgType type, const QString& message, QHashlogVars=*logVars; } } -QString LogMessage::toString(const QString& msgFormat, const QString& timestampFormat) const { +QString LogMessage::toString(const QString& msgFormat, const QString& timestampFormat) const +{ QString decorated=msgFormat+"\n"; decorated.replace("{msg}",message); - if (decorated.contains("{timestamp}")) { + if (decorated.contains("{timestamp}")) + { decorated.replace("{timestamp}",timestamp.toString(timestampFormat)); } @@ -34,21 +38,22 @@ QString LogMessage::toString(const QString& msgFormat, const QString& timestampF typeNr.setNum(type); decorated.replace("{typeNr}",typeNr); - switch (type) { - case QtDebugMsg: - decorated.replace("{type}","DEBUG"); - break; - case QtWarningMsg: - decorated.replace("{type}","WARNING"); - break; - case QtCriticalMsg: - decorated.replace("{type}","CRITICAL"); - break; - case QtFatalMsg: - decorated.replace("{type}","FATAL"); - break; - default: - decorated.replace("{type}",typeNr); + switch (type) + { + case QtDebugMsg: + decorated.replace("{type}","DEBUG"); + break; + case QtWarningMsg: + decorated.replace("{type}","WARNING"); + break; + case QtCriticalMsg: + decorated.replace("{type}","CRITICAL"); + break; + case QtFatalMsg: + decorated.replace("{type}","FATAL"); + break; + default: + decorated.replace("{type}",typeNr); } decorated.replace("{file}",file); @@ -60,9 +65,11 @@ QString LogMessage::toString(const QString& msgFormat, const QString& timestampF decorated.replace("{thread}",threadId); // Fill in variables - if (decorated.contains("{") && !logVars.isEmpty()) { + if (decorated.contains("{") && !logVars.isEmpty()) + { QList keys=logVars.keys(); - foreach (QString key, keys) { + foreach (QString key, keys) + { decorated.replace("{"+key+"}",logVars.value(key)); } } @@ -70,6 +77,7 @@ QString LogMessage::toString(const QString& msgFormat, const QString& timestampF return decorated; } -QtMsgType LogMessage::getType() const { +QtMsgType LogMessage::getType() const +{ return type; } diff --git a/YACReaderLibrary/server/lib/logging/logmessage.h b/YACReaderLibrary/server/lib/logging/logmessage.h index 433d949d..d6228cba 100644 --- a/YACReaderLibrary/server/lib/logging/logmessage.h +++ b/YACReaderLibrary/server/lib/logging/logmessage.h @@ -9,6 +9,7 @@ #include #include #include +#include "logglobal.h" /** Represents a single log message together with some data @@ -20,16 +21,17 @@ - {typeNr} Type of the message in numeric format (0-3) - {type} Type of the message in string format (DEBUG, WARNING, CRITICAL, FATAL) - {thread} ID number of the thread - - {msg} Message text (only useable in msgFormat) - - {file} Filename where the message was generated # - - {function} Function where the message was generated # - - {line} Line number where the message was generated # + - {msg} Message text - {xxx} For any user-defined logger variable - # The macros qDebug()...qFatal() dont fill these variable in case of QT versions before 5.0. + Plus some new variables since QT 5.0, only filled when compiled in debug mode: + + - {file} Filename where the message was generated + - {function} Function where the message was generated + - {line} Line number where the message was generated */ -class LogMessage +class DECLSPEC LogMessage { Q_DISABLE_COPY(LogMessage) public: