1 
2 /*  $Id: listener.cpp 605543 2020-04-13 12:14:53Z foleyjp $
3  * ===========================================================================
4  *
5  *                            PUBLIC DOMAIN NOTICE
6  *               National Center for Biotechnology Information
7  *
8  *  This software/database is a "United States Government Work" under the
9  *  terms of the United States Copyright Act.  It was written as part of
10  *  the author's official duties as a United States Government employee and
11  *  thus cannot be copyrighted.  This software/database is freely available
12  *  to the public for use. The National Library of Medicine and the U.S.
13  *  Government have not placed any restriction on its use or reproduction.
14  *
15  *  Although all reasonable efforts have been taken to ensure the accuracy
16  *  and reliability of the software and data, the NLM and the U.S.
17  *  Government do not and cannot warrant the performance or results that
18  *  may be obtained by using this software or data. The NLM and the U.S.
19  *  Government disclaim all warranties, express or implied, including
20  *  warranties of performance, merchantability or fitness for any particular
21  *  purpose.
22  *
23  *  Please cite the author in any work or product based on this material.
24  *
25  * ===========================================================================
26  *
27  * Author: Justin Foley
28  *
29  * File Description:
30  *  Objtools message listener classes - based on ILineErrorListener
31  *
32  */
33 
34 
35 
36 #include  <ncbi_pch.hpp>
37 #include <objtools/logging/message.hpp>
38 #include <objtools/logging/listener.hpp>
39 
40 BEGIN_NCBI_SCOPE
BEGIN_SCOPE(objects)41 BEGIN_SCOPE(objects)
42 
43 bool IObjtoolsListener::SevEnabled(EDiagSev severity) const
44 {
45     return (severity > eDiag_Info);
46 }
47 
48 
49 CObjtoolsListener::~CObjtoolsListener() = default;
50 
51 
52 bool
PutMessage(const IObjtoolsMessage & message)53 CObjtoolsListener::PutMessage(const IObjtoolsMessage& message)
54 {
55     m_Messages.emplace_back(message.Clone());
56     return true;
57 }
58 
59 
60 void
PutProgress(const string & message,const Uint8 num_done,const Uint8 num_total)61 CObjtoolsListener::PutProgress(
62     const string& message,
63     const Uint8 num_done,
64     const Uint8 num_total)
65 {
66     // NB: Some other classes rely on the message fitting in one line.
67 
68     // NB: New attributes or inner elements could be added to the resulting
69     //     message at any time, so make no assumptions.
70 
71     if( ! m_pProgressOstrm ) {
72         // no stream to write to
73         return;
74     }
75 
76     *m_pProgressOstrm << "<message severity=\"INFO\" ";
77 
78     if( num_done > 0 ) {
79         *m_pProgressOstrm << "num_done=\"" << num_done << "\" ";
80     }
81 
82     if( num_total > 0 ) {
83         *m_pProgressOstrm << "num_total=\"" << num_total << "\" ";
84     }
85 
86     if( message.empty() ) {
87         *m_pProgressOstrm  << " />";
88     } else {
89         *m_pProgressOstrm  << " >";
90 
91         string sXMLEncodedMessage = NStr::XmlEncode(message);
92 
93         // some functionality relies on progress messages fitting into
94         // one line, so we escape newlines (just in case) while
95         // we write it.
96         ITERATE( string, msg_it, sXMLEncodedMessage ) {
97             const char ch = *msg_it;
98             switch(ch) {
99             case '\r':
100                 *m_pProgressOstrm << "&#xD;";
101                 break;
102             case '\n':
103                 *m_pProgressOstrm << "&#xA;";
104                 break;
105             default:
106                 *m_pProgressOstrm << ch;
107                 break;
108             }
109         }
110 
111         *m_pProgressOstrm << "</message>" << NcbiEndl;
112     }
113 
114     m_pProgressOstrm->flush();
115 }
116 
117 
SetProgressOstream(CNcbiOstream * pProgressOstream)118 void CObjtoolsListener::SetProgressOstream(CNcbiOstream* pProgressOstream)
119 {
120     m_pProgressOstrm = pProgressOstream;
121 }
122 
123 
124 const IObjtoolsMessage&
GetMessage(size_t index) const125 CObjtoolsListener::GetMessage(size_t index) const
126 {
127     return *m_Messages[index].get();
128 }
129 
130 
131 size_t
Count() const132 CObjtoolsListener::Count() const
133 {
134     return m_Messages.size();
135 }
136 
137 
138 void
ClearAll()139 CObjtoolsListener::ClearAll() {
140     m_Messages.clear();
141 }
142 
143 
LevelCount(EDiagSev severity) const144 size_t CObjtoolsListener::LevelCount(EDiagSev severity) const {
145     size_t uCount = 0;
146     for (const auto& pMessage : m_Messages) {
147         if (pMessage->GetSeverity() == severity) {
148             ++uCount;
149         }
150     }
151     return uCount;
152 }
153 
154 
Dump(CNcbiOstream & ostr) const155 void CObjtoolsListener::Dump(CNcbiOstream& ostr) const
156 {
157     if (m_Messages.empty()) {
158         ostr << "(( No messages ))" << endl;
159         return;
160     }
161     for (const auto& pMessage : m_Messages) {
162         pMessage->Dump(ostr);
163     }
164 }
165 
166 
DumpAsXML(CNcbiOstream & ostr) const167 void CObjtoolsListener::DumpAsXML(CNcbiOstream& ostr) const
168 {
169 
170     if (m_Messages.empty()) {
171         ostr << "(( No messages ))" << endl;
172         return;
173     }
174 
175     for (const auto& pMessage : m_Messages) {
176         pMessage->DumpAsXML(ostr);
177     }
178 }
179 
180 
181 CObjtoolsListener::TConstIterator
begin() const182 CObjtoolsListener::begin() const {
183     return TConstIterator(m_Messages.cbegin());
184 }
185 
186 
187 CObjtoolsListener::TConstIterator
end() const188 CObjtoolsListener::end() const {
189     return TConstIterator(m_Messages.cend());
190 }
191 
192 
CObjtoolsListenerLevel(int accept_level)193 CObjtoolsListenerLevel::CObjtoolsListenerLevel(int accept_level)
194     : m_AcceptLevel(accept_level) {}
195 
196 
197 CObjtoolsListenerLevel::~CObjtoolsListenerLevel() = default;
198 
199 
PutMessage(const IObjtoolsMessage & message)200 bool CObjtoolsListenerLevel::PutMessage(const IObjtoolsMessage& message)
201 {
202     CObjtoolsListener::PutMessage(message);
203     return (static_cast<int>(message.GetSeverity()) <= m_AcceptLevel);
204 }
205 
206 
CObjtoolsListenerLenient()207 CObjtoolsListenerLenient::CObjtoolsListenerLenient()
208     : CObjtoolsListenerLevel(eDiag_Info) {}
209 
210 
CObjtoolsListenerStrict()211 CObjtoolsListenerStrict::CObjtoolsListenerStrict()
212    : CObjtoolsListenerLevel(eDiagSevMax+1) {}
213 
214 
215 END_SCOPE(objects)
216 END_NCBI_SCOPE
217 
218