LOGO

RestFrames  v1.0.1
RestFrames HEP Event Analysis Software Library
RFLog.cc
Go to the documentation of this file.
1 // RestFrames: particle physics event analysis library
3 // --------------------------------------------------------------------
4 // Copyright (c) 2014-2016, Christopher Rogan
14 // This file is part of RestFrames.
15 //
16 // RestFrames is free software; you can redistribute it and/or modify
17 // it under the terms of the GNU General Public License as published by
18 // the Free Software Foundation; either version 2 of the License, or
19 // (at your option) any later version.
20 //
21 // RestFrames is distributed in the hope that it will be useful,
22 // but WITHOUT ANY WARRANTY; without even the implied warranty of
23 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 // GNU General Public License for more details.
25 //
26 // You should have received a copy of the GNU General Public License
27 // along with RestFrames. If not, see <http://www.gnu.org/licenses/>.
29 
30 #include <iomanip>
31 #include <stdlib.h>
32 #include "RestFrames/RFLog.hh"
33 #include "RestFrames/RFBase.hh"
34 
35 namespace RestFrames {
36 
37  class RFBase;
38 
39  // default RFLog parameters
40  std::map<RestFrames::LogType,bool> RFLog::m_PrintMap = InitPrintMap();
41  std::ostream* RFLog::m_Ostr = &std::cerr;
42  bool RFLog::m_Color = true;
43  int RFLog::m_NMAX = 100;
44 
45  RFLog::RFLog(const std::string& source, LogType def_type)
46  : m_DefType(def_type)
47  {
48  Init();
49  SetSource(source);
50  }
51 
52  RFLog::RFLog(){
53  Init();
54  }
55 
56  RFLog g_Log("RestFrames Global");
57 
58  RFLog::~RFLog() {}
59 
60  void RFLog::Init(){
61  m_Source = "Unknown";
62  m_CurType = m_DefType;
63  m_Message.str("");
64  m_TypeMap[LogVerbose] = "VERBOSE";
65  m_TypeMap[LogDebug] = "DEBUG";
66  m_TypeMap[LogInfo] = "INFO";
67  m_TypeMap[LogWarning] = "WARNING";
68  m_TypeMap[LogError] = "ERROR";
69 
70  m_ColorMap[LogVerbose] = "\x1b[36m";
71  m_ColorMap[LogDebug] = "\x1b[33m";
72  m_ColorMap[LogInfo] = "\x1b[32m";
73  m_ColorMap[LogWarning] = "\x1b[35m";
74  m_ColorMap[LogError] = "\x1b[31m";
75  }
76 
77  std::map<LogType,bool> InitPrintMap(){
78  std::map<LogType,bool> m;
79  m[LogVerbose] = false;
80  m[LogDebug] = false;
81  m[LogInfo] = true;
82  m[LogWarning] = true;
83  m[LogError] = true;
84  return m;
85  }
86 
87  std::string RFLog::GetFormattedSource() const {
88  std::string source_name = m_Source;
89  if (source_name.size() > 22){
90  source_name = source_name.substr( 0, 22 - 3 );
91  source_name += "...";
92  }
93  return source_name;
94  }
95 
96  std::string RFLog::GetFormattedMessage(const std::string& message) {
97  std::string output = "";
98  int N = message.size();
99  int OFF = 18;
100  if(N-OFF > m_NMAX){
101  int Ncut = (N-OFF)/m_NMAX;
102  if((N-OFF)%m_NMAX == 0)
103  Ncut--;
104  std::string::size_type previous_pos = 0;
105  for(int i = 0; i <= Ncut; i++){
106  int off = m_NMAX;
107  if(i == 0) off += OFF;
108  std::string line = message.substr(previous_pos, off);
109  if(i > 0){
110  if(m_Color)
111  output += m_ColorMap[m_CurType]+"<...>\x1b[0m ...";
112  else
113  output += "<...> ...";
114  }
115  output += line;
116  previous_pos += off;
117  if(int(previous_pos) != N && i != Ncut) output += "...\n";
118  }
119  } else {
120  output = message;
121  }
122  return output;
123  }
124 
125  void RFLog::Send(){
126  std::string source_name = GetFormattedSource();
127  std::string message = m_Message.str();
128  std::string::size_type previous_pos = 0, current_pos = 0;
129  if(m_PrintMap[m_CurType] && m_Ostr){
130  std::string prefix;
131  if(m_Color)
132  prefix = m_ColorMap[m_CurType]+"<"+m_TypeMap[m_CurType]+">";
133  else
134  prefix = "<"+m_TypeMap[m_CurType]+">";
135  for(int i = 0; i < 8-int(m_TypeMap[m_CurType].size()); i++){
136  prefix += ' ';
137  }
138  prefix += source_name+": ";
139  if(m_Color)
140  prefix +="\x1b[0m";
141  while (true) {
142  current_pos = message.find( '\n', previous_pos );
143  std::string line = message.substr( previous_pos, current_pos - previous_pos );
144 
145  std::ostringstream message_to_send;
146  message_to_send.setf(std::ios::adjustfield, std::ios::left);
147  line = GetFormattedMessage(prefix+line);
148  message_to_send << line << std::endl;
149 
150  *m_Ostr << message_to_send.str();
151  m_Ostr->flush();
152 
153  if (current_pos == message.npos) break;
154  previous_pos = current_pos + 1;
155  }
156  }
157 
158  if (m_CurType == LogError)
159  throw RestFramesException(m_Message.str());
160 
161  m_Message.str("");
162  m_CurType = m_DefType;
163  return;
164  }
165 
166  RFLog& RFLog::EndMessage(RFLog& log){
167  log.Send();
168  return log;
169  }
170 
171  void RFLog::PrintObject(const RFBase* objPtr){
172  m_Message << objPtr->PrintString(LogVerbose);
173  }
174 
175  template <class T>
176  void RFLog::PrintList(const RFList<T>* listPtr){
177  int N = listPtr->GetN();
178  for(int i = 0; i < N; i++)
179  m_Message << listPtr->Get(i).GetName() << " ";
180  }
181 
182  void RFLog::SetSource(const std::string& source){
183  m_Source = source;
184  }
185 
186  void SetLogPrint(LogType type, bool print){
187  RFLog::m_PrintMap[type] = print;
188  }
189 
190  void SetLogPrint(bool print){
191  for (std::map<LogType, bool>::iterator m = RFLog::m_PrintMap.begin();
192  m != RFLog::m_PrintMap.end(); ++m)
193  m->second = (m->second && print);
194  }
195 
196  void SetLogStream(std::ostream* ostr){
197  if(ostr) RFLog::m_Ostr = ostr;
198  }
199 
200  void SetLogColor(bool color){
201  RFLog::m_Color = color;
202  }
203 
204  void SetLogMaxWidth(int NMAX){
205  if(NMAX > 0) RFLog::m_NMAX = NMAX;
206  }
207 
208  template <> RFLog& RFLog::operator << (const RFBase* arg){
209  PrintObject(arg);
210  return *this;
211  }
212 
213  template <> RFLog& RFLog::operator << (const RFBaseList* arg){
214  PrintList(arg);
215  return *this;
216  }
217 
218  const RFBase* Log(const RFBase& obj){ return (const RFBase*)&obj; }
219  const RFBase* Log(const RFBase* ptr){ return (const RFBase*)ptr; }
220 
221 }