Imported Upstream version 0.8~alpha1
[platform/upstream/syncevolution.git] / src / client-api / src / include / common / base / Log.h
1 /*
2  * Funambol is a mobile platform developed by Funambol, Inc. 
3  * Copyright (C) 2003 - 2007 Funambol, Inc.
4  * 
5  * This program is free software; you can redistribute it and/or modify it under
6  * the terms of the GNU Affero General Public License version 3 as published by
7  * the Free Software Foundation with the addition of the following permission 
8  * added to Section 15 as permitted in Section 7(a): FOR ANY PART OF THE COVERED
9  * WORK IN WHICH THE COPYRIGHT IS OWNED BY FUNAMBOL, FUNAMBOL DISCLAIMS THE 
10  * WARRANTY OF NON INFRINGEMENT  OF THIRD PARTY RIGHTS.
11  * 
12  * This program is distributed in the hope that it will be useful, but WITHOUT
13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14  * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
15  * details.
16  * 
17  * You should have received a copy of the GNU Affero General Public License 
18  * along with this program; if not, see http://www.gnu.org/licenses or write to
19  * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
20  * MA 02110-1301 USA.
21  * 
22  * You can contact Funambol, Inc. headquarters at 643 Bair Island Road, Suite 
23  * 305, Redwood City, CA 94063, USA, or at email address info@funambol.com.
24  * 
25  * The interactive user interfaces in modified source and object code versions
26  * of this program must display Appropriate Legal Notices, as required under
27  * Section 5 of the GNU Affero General Public License version 3.
28  * 
29  * In accordance with Section 7(b) of the GNU Affero General Public License
30  * version 3, these Appropriate Legal Notices must retain the display of the
31  * "Powered by Funambol" logo. If the display of the logo is not reasonably 
32  * feasible for technical reasons, the Appropriate Legal Notices must display
33  * the words "Powered by Funambol".
34  */
35
36 #ifndef INCL_LOG
37     #define INCL_LOG
38 /** @cond DEV */
39
40     #include "base/fscapi.h"
41     #include "base/util/StringBuffer.h"
42
43     /** prefix for error messages */
44     #define LOG_ERROR "ERROR"
45     /** prefix for informational messages */
46     #define LOG_INFO  "INFO"
47     /** prefix for debug or developer messages */
48     #define LOG_DEBUG "DEBUG"
49
50     /** default is to create this file in the current directory */
51     #define LOG_NAME "synclog.txt"
52 #include "base/globalsdef.h"
53
54 BEGIN_NAMESPACE
55
56     /**
57      * valid parameters for setLevel()
58      */
59     typedef enum {
60         /**
61          * log level not configured: if used in setLevel(), then only
62          * error messages will be printed
63          */
64         LOG_LEVEL_NONE  = 0,
65         /**
66          * errors and info messages for users and developers
67          * will be printed: use this to keep the log consise and
68          * small
69          */
70         LOG_LEVEL_INFO  = 1,
71         /**
72          * all messages will be printed: the log can become very large!
73          */
74         LOG_LEVEL_DEBUG = 2,
75     } LogLevel;
76
77     class Log {
78
79     private:
80
81         /**
82          * Which log level is set?
83          */
84         LogLevel logLevel;
85
86         /**
87          * the singleton implementing logging
88          */
89         static Log *logger;
90
91     public:
92
93         Log() : logLevel(LOG_LEVEL_INFO) {}
94         virtual ~Log() {}
95
96         /**
97          * Grants access to the singleton which implements logging.
98          * The implementation of this function and thus the Log
99          * class itself is platform specific: if no Log instance
100          * has been set yet, then this call has to create one.
101          */
102         static Log &instance();
103
104         /**
105          * Overrides the default Log implementation. The Log class
106          * itself will never delete the active logger.
107          *
108          * @param logger    will be used for all future logging activities;
109          *                  NULL is allowed and implies that the default
110          *                  Log implementation will be created if needed
111          */
112         static void setLogger(Log *logger) { Log::logger = logger; }
113
114         /** clients can use #ifdef to detect this new feature */
115 # define LOG_HAVE_SET_LOGGER 1
116
117         /**
118          * Sets the directory where the log file will be created,
119          * which is done in reset() or any of the logging functions.
120          */
121         virtual void setLogPath(const char*  configLogPath) = 0;
122
123         /**
124          * Sets the file name of the log file without creating it;
125          * that is done in reset() or any of the logging functions.
126          */
127         virtual void setLogName(const char*  configLogName) = 0;
128
129         /**
130          * creates the log file under the selected name and path,
131          * optionally logging the given title
132          */
133         virtual void reset(const char*  title = NULL) = 0;
134
135         virtual void setLevel(LogLevel level) { logLevel = level; }
136         virtual LogLevel getLevel() { return logLevel; }
137         virtual bool isLoggable(LogLevel level) { return level <= logLevel; }
138
139         /**
140          * error(), info(), developer(), debug() all print one message,
141          * using printf() style formatting. Whether the message is really
142          * written into the log file depends on the current log level
143          * (see LogLevel above).
144          *
145          * Which of these calls is the right one for a certain message
146          * is a somewhat subjective choice. Here is a definition how they
147          * are supposed to be used:
148          * - error: severe problem which the user and developer have to
149          *          know about
150          * - info: information about a sync session which the user
151          *         will want to read during/after each sync session
152          * - developer: information about a sync session that is not
153          *              interesting for a user (for example, because it
154          *              is constant and already known) but which should
155          *              be in each log because developers need to know
156          *              it. Messages logged with this calls will be included
157          *              at LOG_LEVEL_INFO, therefore messages should be small and
158          *              not recur so that the log file size remains small.
159          * - debug: most detailed logging, messages may be arbitrarily large
160          *
161          * Here is a decision tree which helps to pick the right level:
162          * - an error: => error()
163          * - it changes during each sync or marks important steps
164          *   in the sync: info()
165          * - small, non-recurring message which is important for developers
166          *   who read a log produced at LOG_LEVEL_INFO: developer()
167          * - everything else: debug()
168          */
169         virtual void error(const char*  msg, ...) = 0;
170         virtual void info(const char*  msg, ...) = 0;
171         virtual void developer(const char* msg, ...) = 0;
172         virtual void debug(const char*  msg, ...) = 0;
173
174         /** clients can use #ifdef to detect this new feature */
175 # define LOG_HAVE_DEVELOPER 1
176
177         /**
178          * Adds a fixed string to each following line of output. NULL
179          * removes the prefix again. Some logging implementations
180          * might ignore the prefix. The prefix is copied by the
181          * implementation, i.e. the caller can free it after this
182          * call.
183          */
184         virtual void setPrefix(const char *prefix) {
185             // Avoid compiler warning
186             prefix = NULL;
187         }
188
189         /**
190          * Returns the log file size [bytes].
191          */
192         virtual size_t getLogSize() = 0;
193     };
194
195 # define LOG Log::instance()
196
197
198 END_NAMESPACE
199
200 /** @endcond */
201 #endif