| /** @name log.cpp |
| ------------------------------------------------------------------F----------- |
| |
| * Licensed to the Apache Software Foundation (ASF) under one |
| * or more contributor license agreements. See the NOTICE file |
| * distributed with this work for additional information |
| * regarding copyright ownership. The ASF licenses this file |
| * to you under the Apache License, Version 2.0 (the |
| * "License"); you may not use this file except in compliance |
| * with the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, |
| * software distributed under the License is distributed on an |
| * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| * KIND, either express or implied. See the License for the |
| * specific language governing permissions and limitations |
| * under the License. |
| |
| ----------------------------------------------------------------------------- |
| |
| Description: This file contains class LogFacility |
| |
| ----------------------------------------------------------------------------- |
| |
| |
| 6/24/1999 Initial creation |
| 7/19/1999 logError(const ErrorInfo & crclErrorInfo) added |
| |
| -------------------------------------------------------------------------- */ |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Include dependencies */ |
| /* ----------------------------------------------------------------------- */ |
| |
| #include <time.h> |
| #include "uima/log.hpp" |
| |
| #include "uima/trace.hpp" |
| #include "uima/comp_ids.h" |
| #include "uima/msg.h" |
| #include "uima/resmgr.hpp" |
| #include "uima/exceptions.hpp" |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Constants */ |
| /* ----------------------------------------------------------------------- */ |
| |
| #define UIMA_LOG_APPLICATION_KEY_UNKNOWN _TEXT("???") |
| const size_t UIMA_LOG_STATIC_CONVERSION_BUFSIZE = 1024; |
| static apr_pool_t * logPool=0; |
| static apr_thread_mutex_t * logMutex=0; |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Forward declarations */ |
| /* ----------------------------------------------------------------------- */ |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Types / Classes */ |
| /* ----------------------------------------------------------------------- */ |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Private Implementation */ |
| /* ----------------------------------------------------------------------- */ |
| namespace uima { |
| FileLogger::FileLogger(string filename) : iv_logfile(0) { |
| iv_logfile = fopen(filename.c_str(),"a"); |
| if (iv_logfile == NULL) { //Need to handle this better |
| //cerr << "Could not open the log file " << cpszLogFile << endl; |
| string str = "Could not open the log file "; |
| str += filename; |
| UIMA_EXC_THROW_NEW(Uima_runtime_error, |
| UIMA_MSG_ID_LITERAL_STRING, |
| UIMA_MSG_ID_LITERAL_STRING, |
| ErrorMessage(UIMA_MSG_ID_LITERAL_STRING, str.c_str()), |
| ErrorInfo::unrecoverable); |
| } |
| } |
| |
| void FileLogger::log(LogStream::EnEntryType enType, |
| string cpszClass, |
| string cpszMethod, |
| string cpszMsg, |
| long lUserCode) |
| /* ----------------------------------------------------------------------- */ |
| { |
| //write to local log file if one is available |
| string message = cpszClass + " "; |
| if (cpszMethod.length() >0) { |
| message += cpszMethod + " "; |
| } |
| message += cpszMsg; |
| message = format(enType, message, lUserCode); |
| fwrite(message.c_str(), 1, message.size(), iv_logfile); |
| fflush(iv_logfile); |
| } |
| |
| std::string FileLogger::format(LogStream::EnEntryType enType, |
| const string & cpszMsg, |
| long lUserCode) { |
| |
| time_t rawtime; |
| time ( &rawtime ); |
| string currts = ctime(&rawtime); |
| |
| stringstream str; |
| str << currts.substr(0,currts.length()-1); |
| |
| //map enType to string |
| switch (enType) { |
| case LogStream::EnWarning : |
| str << " WARNING: "; |
| str << " RC=" << lUserCode << " "; |
| break; |
| case LogStream::EnError : |
| str << " SEVERE: "; |
| str << " RC=" << lUserCode << " "; |
| break; |
| default: |
| str << " INFO: "; |
| if (lUserCode !=0) { |
| str << " RC=" << lUserCode << " "; |
| } |
| } |
| |
| str << cpszMsg << endl; |
| |
| return str.str(); |
| } |
| |
| TyMessageId LogFacility::getTypeAsMessageId(LogStream::EnEntryType enType) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| switch (enType) { |
| case LogStream::EnMessage : |
| return(UIMA_MSG_ID_LOG_MESSAGE); |
| case LogStream::EnWarning : |
| return(UIMA_MSG_ID_LOG_WARNING); |
| case LogStream::EnError : |
| return(UIMA_MSG_ID_LOG_ERROR); |
| default: |
| assertWithMsg(false, _TEXT("Unknown EnLogEntryType")); //lint !e506: Constant value Boolean |
| } |
| return(0); /* shutup compiler */ |
| } |
| |
| void LogFacility::doLog(LogStream::EnEntryType enType, const TCHAR * cpszMsg, long lUserCode) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| apr_thread_mutex_lock(logMutex); |
| string method=""; |
| if (isLoggable(enType)) { |
| for (int i=0; i < vecLoggers.size(); i++) { |
| vecLoggers.at(i)->log(enType,this->iv_strOrigin, |
| method,cpszMsg,lUserCode); |
| } |
| } |
| apr_thread_mutex_unlock(logMutex); |
| } |
| |
| bool LogFacility::isLoggable(LogStream::EnEntryType enType) const { |
| ///LogStream::EnEntryType minLogLevel = ResourceManager::getInstance().getLoggingLevel(); |
| if (enType < iv_logLevel) { |
| return false; |
| } |
| return true; |
| } |
| |
| void LogFacility::setLogLevel(LogStream::EnEntryType enType) { |
| ///LogStream::EnEntryType minLogLevel = ResourceManager::getInstance().getLoggingLevel(); |
| iv_logLevel = enType; |
| } |
| |
| void LogFacility::log(LogStream::EnEntryType enType, const TCHAR * cpszMsg, long lUserCode) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| doLog(enType, cpszMsg, lUserCode); |
| |
| if (enType == LogStream::EnError) { |
| LogFacility * pclThis = CONST_CAST(LogFacility *, this); |
| assert(pclThis == this); |
| //remember last error as string/number |
| pclThis->iv_lLastUserCode = lUserCode; |
| pclThis->iv_strLastError = string(cpszMsg); |
| //reset error info object |
| pclThis->iv_errInfo.reset(); |
| } |
| } |
| |
| |
| void LogFacility::log(LogStream::EnEntryType enType, ErrorInfo const & errInfo) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| doLog(enType, errInfo.asString().c_str()); |
| |
| LogFacility * pclThis = CONST_CAST(LogFacility *, this); |
| assert(pclThis == this); |
| //remember last error as error info object |
| pclThis->iv_errInfo = errInfo; |
| //reset string/number |
| // MSV6 compile error: pclThis->iv_strLastError.clear(); |
| pclThis->iv_strLastError = std::string(); |
| pclThis->iv_lLastUserCode = 0; |
| } |
| |
| |
| void LogFacility::log(LogStream::EnEntryType enType, const icu::UnicodeString & ustrMsg, long lUserCode) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| string strMsg; |
| UnicodeStringRef ref(ustrMsg); |
| ref.extract(strMsg, CCSID::getDefaultName()); |
| log(enType, strMsg.c_str(), lUserCode); |
| } |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Implementation */ |
| /* ----------------------------------------------------------------------- */ |
| |
| LogStream & LogStream::flush() { |
| this->stringstream::flush(); |
| iv_pLogFacility->flushLogStream(); |
| str(""); |
| return (*this); |
| } |
| |
| LogStream & LogFacility::getLogStream(LogStream::EnEntryType enLogEntryType) { |
| iv_logStream.iv_enLogEntryType = enLogEntryType; |
| flushLogStream(); |
| return iv_logStream; |
| } |
| |
| void LogFacility::flushLogStream() { |
| string strMsg = iv_logStream.str(); |
| if (strMsg.size() == 0) { |
| return; |
| } |
| log(iv_logStream.iv_enLogEntryType, strMsg.c_str()); |
| } |
| |
| |
| LogFacility::LogFacility(icu::UnicodeString const & crEngineName): |
| iv_lLastUserCode(0), |
| iv_logStream(*this, LogStream::EnMessage), |
| vecLoggers(ResourceManager::getInstance().getLoggers()), |
| iv_logLevel(ResourceManager::getInstance().getLoggingLevel()) { |
| if (logPool == NULL) { |
| apr_status_t rv = apr_pool_create( &logPool,NULL ); |
| if ( rv == APR_SUCCESS ) { |
| UnicodeStringRef ref(crEngineName); |
| ref.extract(iv_strOrigin, CCSID::getDefaultName() ); |
| apr_thread_mutex_create(&logMutex,APR_THREAD_MUTEX_UNNESTED, logPool); |
| } else { |
| UIMA_EXC_THROW_NEW(ExcOutOfMemory, |
| UIMA_ERR_ENGINE_OUT_OF_MEMORY, |
| UIMA_MSG_ID_EXC_OUT_OF_MEMORY, |
| ErrorMessage(UIMA_MSG_ID_EXCON_CREATING_POOL_FOR_CLASS,"uima::LogFacility"), |
| ErrorInfo::unrecoverable); |
| } |
| } |
| } |
| |
| LogFacility::LogFacility(icu::UnicodeString const & crEngineName, |
| LogStream::EnEntryType crLoggingLevel): |
| iv_lLastUserCode(0), |
| iv_logStream(*this, crLoggingLevel), |
| vecLoggers(ResourceManager::getInstance().getLoggers()), |
| iv_logLevel(crLoggingLevel) { |
| |
| if (logPool == NULL) { |
| apr_status_t rv = apr_pool_create( &logPool,NULL ); |
| if ( rv == APR_SUCCESS ) { |
| UnicodeStringRef ref(crEngineName); |
| ref.extract(iv_strOrigin, CCSID::getDefaultName() ); |
| apr_thread_mutex_create(&logMutex,APR_THREAD_MUTEX_UNNESTED, logPool); |
| } else { |
| UIMA_EXC_THROW_NEW(ExcOutOfMemory, |
| UIMA_ERR_ENGINE_OUT_OF_MEMORY, |
| UIMA_MSG_ID_EXC_OUT_OF_MEMORY, |
| ErrorMessage(UIMA_MSG_ID_EXCON_CREATING_POOL_FOR_CLASS,"uima::LogFacility"), |
| ErrorInfo::unrecoverable); |
| } |
| } |
| } |
| |
| LogFacility::~LogFacility() { |
| flushLogStream(); |
| } |
| |
| const TCHAR * LogFacility::getLastErrorAsCStr(void) const { |
| /* ----------------------------------------------------------------------- */ |
| LogFacility * pclThis = CONST_CAST(LogFacility *, this); |
| ErrorInfo errInfo = getLastError(); |
| if (errInfo.getErrorId() == UIMA_ERR_NONE) { |
| return (NULL); |
| } |
| pclThis->iv_strLastError = getLastError().asString(); |
| return(iv_strLastError.c_str()); |
| } |
| |
| ErrorInfo const & LogFacility::getLastError() const { |
| /* ----------------------------------------------------------------------- */ |
| // check if we have a string or info based information on last error |
| if (iv_strLastError.length() > 0) { |
| // if we have error string the error object must be clear |
| assert(iv_errInfo.getErrorId() == UIMA_ERR_NONE); |
| // now set up the object with the string information |
| LogFacility * pclThis = CONST_CAST(LogFacility *, this); |
| assert(pclThis == this); |
| if (iv_lLastUserCode == 0) { |
| pclThis->iv_errInfo.setErrorId(UIMA_ERR_USER_ANNOTATOR_ERROR_UNSPECIFIED); |
| } else { |
| pclThis->iv_errInfo.setErrorId(iv_lLastUserCode); |
| } |
| ErrorMessage msg(UIMA_MSG_ID_LOG_TO_ERROR_INFO, iv_strOrigin); |
| msg.addParam(iv_strLastError); |
| pclThis->iv_errInfo.setMessage(msg); |
| pclThis->iv_errInfo.setSeverity(ErrorInfo::unrecoverable); |
| // now that the information is transferred into the object clear string |
| pclThis->iv_lLastUserCode = 0; |
| // MSV6 compile error: |
| //pclThis->iv_strLastError.clear(); |
| pclThis->iv_strLastError = std::string(); |
| } |
| assert(iv_strLastError.length() == 0); |
| assert(iv_lLastUserCode == 0); |
| return iv_errInfo; |
| } |
| |
| |
| void LogFacility::logWarning(const ErrorInfo & errInfo) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| log(LogStream::EnWarning, errInfo); |
| } |
| |
| |
| void LogFacility::logError(const ErrorInfo & errInfo) const |
| /* ----------------------------------------------------------------------- */ |
| { |
| log(LogStream::EnError, errInfo); |
| } |
| |
| } //namespace uima |
| /* <EOF> */ |
| |
| |
| |
| |