presage
0.8.7
|
00001 00002 /****************************************************** 00003 * Presage, an extensible predictive text entry system 00004 * --------------------------------------------------- 00005 * 00006 * Copyright (C) 2008 Matteo Vescovi <matteo.vescovi@yahoo.co.uk> 00007 00008 This program is free software; you can redistribute it and/or modify 00009 it under the terms of the GNU General Public License as published by 00010 the Free Software Foundation; either version 2 of the License, or 00011 (at your option) any later version. 00012 00013 This program is distributed in the hope that it will be useful, 00014 but WITHOUT ANY WARRANTY; without even the implied warranty of 00015 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00016 GNU General Public License for more details. 00017 00018 You should have received a copy of the GNU General Public License along 00019 with this program; if not, write to the Free Software Foundation, Inc., 00020 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 00021 * 00022 **********(*)*/ 00023 00024 00025 #ifndef PRESAGE_LOGGER 00026 #define PRESAGE_LOGGER 00027 00028 #if HAVE_CONFIG_H 00029 # include <config.h> 00030 #endif 00031 00032 #include <iostream> 00033 00034 00035 // manipulators 00036 struct _SetLevel { std::string _level; }; 00037 00045 inline _SetLevel 00046 setlevel(std::string __l) 00047 { 00048 _SetLevel __x; 00049 __x._level = __l; 00050 return __x; 00051 } 00052 00053 00054 00055 template <class _charT, class _Traits=std::char_traits<_charT> > 00056 class Logger 00057 { 00058 public: 00059 // type definitions 00060 enum Level 00061 { 00062 EMERG = 0, 00063 FATAL = 0, 00064 ALERT = 100, 00065 CRIT = 200, 00066 ERROR = 300, 00067 WARN = 400, 00068 NOTICE = 500, 00069 INFO = 600, 00070 DEBUG = 700, 00071 ALL = 800 00072 }; 00073 00074 // constructors 00075 inline 00076 Logger (std::string logger_name, 00077 std::basic_ostream<_charT,_Traits>& ostr) 00078 : outstream(ostr) 00079 { 00080 init(logger_name, "ERROR"); 00081 } 00082 00083 inline 00084 Logger (std::string logger_name, 00085 std::basic_ostream<_charT,_Traits>& ostr, 00086 const std::string& lvl) 00087 : outstream(ostr) 00088 { 00089 init(logger_name, lvl); 00090 } 00091 00092 inline 00093 void init(const std::string& name, const std::string& lvl) 00094 { 00095 set_name(name); 00096 state = new LoggerState(); 00097 set (state->loggerLevel, lvl); 00098 set (state->currentLevel, lvl); 00099 state->line_beginning = true; 00100 } 00101 00102 // destructor 00103 inline 00104 ~Logger () 00105 { 00106 outstream.flush(); 00107 delete state; 00108 } 00109 00110 00111 // level getters/setters 00112 inline 00113 void 00114 setLevel(const std::string& lvl) const 00115 { 00116 set(state->loggerLevel, lvl); 00117 } 00118 00119 inline 00120 void 00121 setLevel (Level lvl) const 00122 { 00123 state->loggerLevel = lvl; 00124 } 00125 00126 inline 00127 Level 00128 getLevel () const 00129 { 00130 return state->loggerLevel; 00131 } 00132 00133 inline 00134 void 00135 setCurrentLevel (Level lvl) const 00136 { 00137 state->currentLevel = lvl; 00138 } 00139 00140 inline 00141 Level 00142 getCurrentLevel() const 00143 { 00144 return state->currentLevel; 00145 } 00146 00147 inline 00148 bool 00149 shouldLog() const 00150 { 00151 return (state->loggerLevel >= state->currentLevel); 00152 } 00153 00154 // logging method 00155 template<typename T> 00156 friend inline 00157 const Logger& 00158 operator<< (const Logger& lgr, const T& msg) 00159 { 00160 //if (lgr.state->loggerLevel >= lgr.state->currentLevel) 00161 if (lgr.shouldLog()) 00162 { 00163 if (lgr.state->line_beginning) { 00164 lgr.outstream << lgr.name; 00165 lgr.state->line_beginning = false; 00166 } 00167 lgr.outstream << msg; 00168 } 00169 return lgr; 00170 } 00171 00172 // this method is needed by the functions defined by macro 00173 // define_logger_level_manipulator(LEVEL) 00174 // 00175 friend inline 00176 const Logger& 00177 operator<< (const Logger& lgr, const Logger& (*fp)(const Logger&)) 00178 { 00179 (*fp)(lgr); 00180 return lgr; 00181 } 00182 00183 inline 00184 const Logger& 00185 operator<< (_SetLevel __l) const 00186 { 00187 setLevel(__l._level); 00188 return *this; 00189 } 00190 00191 inline 00192 void endl() const 00193 { 00194 //if (state->loggerLevel >= state->currentLevel) 00195 if (shouldLog()) 00196 { 00197 outstream << std::endl; 00198 state->line_beginning = true; 00199 } 00200 } 00201 00202 private: 00203 inline 00204 void 00205 set(Level& level, const std::string& lvl) const 00206 { 00207 if (lvl == "EMERG") { 00208 level = EMERG; 00209 } else if (lvl == "FATAL") { 00210 level = FATAL; 00211 } else if (lvl == "ALERT") { 00212 level = ALERT; 00213 } else if (lvl == "CRIT") { 00214 level = CRIT; 00215 } else if (lvl == "ERROR") { 00216 level = ERROR; 00217 } else if (lvl == "WARN") { 00218 level = WARN; 00219 } else if (lvl == "NOTICE") { 00220 level = NOTICE; 00221 } else if (lvl == "INFO") { 00222 level = INFO; 00223 } else if (lvl == "DEBUG") { 00224 level = DEBUG; 00225 } else if (lvl == "ALL") { 00226 level = ALL; 00227 } else { 00228 level = ERROR; 00229 } 00230 } 00231 00232 inline 00233 void 00234 set_name(const std::string& logger_name) 00235 { 00236 name = "[" + logger_name + "] "; 00237 } 00238 00239 std::string name; 00240 std::basic_ostream <_charT, _Traits>& outstream; 00241 00242 class LoggerState { 00243 public: 00244 bool line_beginning; 00245 Level loggerLevel; 00246 Level currentLevel; 00247 00248 }; 00249 00250 LoggerState* state; 00251 }; 00252 00253 00254 00255 #define define_logger_level_manipulator(LEVEL) \ 00256 template <typename _charT, typename _Traits> \ 00257 inline const Logger<_charT, _Traits>& \ 00258 LEVEL (const Logger<_charT, _Traits>& lgr) \ 00259 { \ 00260 lgr.setCurrentLevel(Logger<_charT, _Traits>::LEVEL); \ 00261 return lgr; \ 00262 } 00263 00264 define_logger_level_manipulator(EMERG ); 00265 define_logger_level_manipulator(FATAL ); 00266 define_logger_level_manipulator(ALERT ); 00267 define_logger_level_manipulator(CRIT ); 00268 define_logger_level_manipulator(ERROR ); 00269 define_logger_level_manipulator(WARN ); 00270 define_logger_level_manipulator(NOTICE); 00271 define_logger_level_manipulator(INFO ); 00272 define_logger_level_manipulator(DEBUG ); 00273 define_logger_level_manipulator(ALL ); 00274 00275 00276 template <typename _charT, typename _Traits> 00277 inline const Logger<_charT, _Traits>& 00278 endl (const Logger<_charT, _Traits>& lgr) 00279 { 00280 lgr.endl(); 00281 return lgr; 00282 } 00283 00284 00285 #endif // PRESAGE_LOGGER