001: /*
002: * Copyright (c) 2000, Jacob Smullyan.
003: *
004: * This is part of SkunkDAV, a WebDAV client. See http://skunkdav.sourceforge.net/
005: * for the latest version.
006: *
007: * SkunkDAV is free software; you can redistribute it and/or
008: * modify it under the terms of the GNU General Public License as published
009: * by the Free Software Foundation; either version 2, or (at your option)
010: * any later version.
011: *
012: * SkunkDAV is distributed in the hope that it will be useful,
013: * but WITHOUT ANY WARRANTY; without even the implied warranty of
014: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015: * General Public License for more details.
016: *
017: * You should have received a copy of the GNU General Public License
018: * along with SkunkDAV; see the file COPYING. If not, write to the Free
019: * Software Foundation, 59 Temple Place - Suite 330, Boston, MA
020: * 02111-1307, USA.
021: */
022:
023: package org.skunk.trace;
024:
025: import java.io.*;
026: import java.lang.reflect.Array;
027: import java.sql.SQLException;
028: import java.sql.SQLWarning;
029: import java.text.MessageFormat;
030: import java.util.*;
031:
032: public class Debug {
033: private static Properties debugProperties;
034: public static final String DEBUG_PROPERTIES = "debug.properties";
035: public static final String DEBUG_LEVEL_PROPERTY = "debugLevel";
036: public static final String LOG_FILE_PROPERTY = "logFile";
037: public static final String DEFAULT_DEBUG_LEVEL_PROPERTY = "defaultDebugLevel";
038: public static final String DEFAULT_LOG_FILE_PROPERTY = "defaultLogFile";
039: public static final String DEBUG_PROPERTIES_FILE = "debugPropertiesFile";
040: public static final int DEFAULT_DEBUG_LEVEL = 5;
041: public static final String DEFAULT_LOG_FILE = null;
042:
043: public static final DebugPriority DP0 = new DebugPriority(0);
044: public static final DebugPriority DP1 = new DebugPriority(1);
045: public static final DebugPriority DP2 = new DebugPriority(2);
046: public static final DebugPriority DP3 = new DebugPriority(3);
047: public static final DebugPriority DP4 = new DebugPriority(4);
048: public static final DebugPriority DP5 = new DebugPriority(5);
049: public static final DebugPriority DP6 = new DebugPriority(6);
050: public static final DebugPriority DP7 = new DebugPriority(7);
051: public static final DebugPriority DP8 = new DebugPriority(8);
052: public static final DebugPriority DP9 = new DebugPriority(9);
053:
054: //change this for production code
055: public static final boolean DEBUG = true;
056:
057: static {
058: initProperties();
059: }
060:
061: public static boolean isDebug(Object caller, DebugPriority priority) {
062: Class daClass = (caller instanceof Class) ? (Class) caller
063: : caller.getClass();
064: return (priority.getPriority() <= getDebugLevel(daClass));
065: }
066:
067: public static void trace(Object caller, DebugPriority priority,
068: String formattedMessage, Object interpolations) {
069: //permit the interpolations argument to be either an array or a single object
070: Object[] interArray = (interpolations instanceof Object[]) ? (Object[]) interpolations
071: : new Object[] { interpolations };
072:
073: Class daClass = (caller instanceof Class) ? (Class) caller
074: : caller.getClass();
075: if (isDebug(daClass, priority)) {
076: String message = MessageFormat.format(formattedMessage,
077: interArray);
078: _trace(daClass, priority, message);
079: }
080: }
081:
082: public static void trace(Object caller, DebugPriority priority,
083: Object message) {
084: Class daClass = (caller instanceof Class) ? (Class) caller
085: : caller.getClass();
086: if (priority.getPriority() > getDebugLevel(daClass))
087: return;
088: _trace(daClass, priority, message);
089: }
090:
091: private static void _trace(Class daClass, DebugPriority priority,
092: Object message) {
093:
094: Date currentDate = new Date();
095: String logFileStr = getLogFile(daClass);
096: /*if no log file is defined for that package,
097: default to System.out and System.err */
098: if (logFileStr != null) {
099: PrintWriter outWriter = null;
100: try {
101: File f = new File(logFileStr);
102: if (!f.exists()) {
103: File parent = f.getParentFile();
104: if (parent != null && !parent.exists()) {
105: parent.mkdirs();
106: }
107: }
108: outWriter = new PrintWriter(new FileWriter(logFileStr,
109: true));
110: } catch (IOException oyVeh) {
111: oyVeh.printStackTrace();
112: }
113: trace(daClass, currentDate, outWriter, message);
114: outWriter.flush();
115: outWriter.close();
116: } else {
117: trace(daClass, currentDate, message);
118: }
119: }
120:
121: private static void trace(Class callClass, Date daDate,
122: PrintWriter pw, Object o) {
123: pw.print(getTraceHeader(callClass, daDate));
124: if (o instanceof SQLWarning)
125: doWarnings(pw, (SQLWarning) o);
126: else if (o instanceof SQLException)
127: doSQLExceptions(pw, (SQLException) o);
128: else if (o instanceof Throwable)
129: ((Throwable) o).printStackTrace(pw);
130: else if (o.getClass().isArray()) {
131: try {
132: for (int i = 0; i < Array.getLength(o); i++) {
133: pw.println(Array.get(o, i));
134: }
135: } catch (Exception e) {
136: pw.println(o);
137: }
138: } else
139: pw.println(o);
140: }
141:
142: private static void trace(Class callClass, Date daDate, Object o) {
143: PrintStream out = (o instanceof Throwable) ? System.err
144: : System.out;
145: out.print(getTraceHeader(callClass, daDate));
146: if (o instanceof SQLWarning)
147: doWarnings(out, (SQLWarning) o);
148: else if (o instanceof SQLException)
149: doSQLExceptions(out, (SQLException) o);
150: else if (o instanceof Throwable)
151: ((Throwable) o).printStackTrace(out);
152: else if (o.getClass().isArray()) {
153: try {
154: for (int i = 0; i < Array.getLength(o); i++) {
155: out.println(Array.get(o, i));
156: }
157: } catch (Exception e) {
158: out.println(o);
159: }
160:
161: } else
162: out.println(o);
163: }
164:
165: private static String getPackage(Object o) {
166: String className;
167: if (o instanceof Class)
168: className = ((Class) o).getName();
169: else
170: className = o.getClass().getName();
171: return className.substring(0, className.lastIndexOf('.'));
172: }
173:
174: private static String getTraceHeader(Class callClass, Date daDate) {
175: return new StringBuffer().append(daDate).append(' ').append(
176: callClass).append(" ==> ").toString();
177: }
178:
179: public static int getDebugLevel(Class caller) {
180: int defaultLevel = getDefaultDebugLevel();
181: String levelStr = debugProperties.getProperty(getPackagedKey(
182: caller, DEBUG_LEVEL_PROPERTY), Integer
183: .toString(defaultLevel));
184: try {
185: return constrain(Integer.parseInt(levelStr), 0, 9);
186: } catch (NumberFormatException numbForX) {
187: doLogError();
188: trace(Debug.class, DebugPriority.DP0, numbForX);
189: }
190: return defaultLevel;
191: }
192:
193: public static int getDefaultDebugLevel() {
194: String defLevStr = debugProperties.getProperty(
195: DEFAULT_DEBUG_LEVEL_PROPERTY, "" + DEFAULT_DEBUG_LEVEL);
196: try {
197: return constrain(Integer.parseInt(defLevStr), 0, 9);
198: } catch (NumberFormatException nafta) {
199: doLogError();
200: trace(Debug.class, DP0, nafta);
201: }
202: return DEFAULT_DEBUG_LEVEL;
203: }
204:
205: private static int constrain(int toBeConstrained, int min, int max) {
206: return Math.min(Math.max(min, toBeConstrained), max);
207: }
208:
209: public static String getLogFile(Class caller) {
210: String logStr = debugProperties.getProperty(getPackagedKey(
211: caller, LOG_FILE_PROPERTY), getDefaultLogFile());
212: return logStr;
213: }
214:
215: public static String getDefaultLogFile() {
216: return debugProperties.getProperty(DEFAULT_LOG_FILE_PROPERTY,
217: DEFAULT_LOG_FILE);
218: }
219:
220: private static String getPackagedKey(Class caller, String key) {
221: return new StringBuffer(getPackage(caller)).append('.').append(
222: key).toString();
223: }
224:
225: private static void initProperties() {
226: debugProperties = new Properties();
227: Object fileProp = System.getProperty(DEBUG_PROPERTIES_FILE);
228: boolean customFile = false;
229: if (fileProp != null) {
230: try {
231: InputStream in = new BufferedInputStream(
232: new FileInputStream(fileProp.toString()));
233: debugProperties.load(in);
234: customFile = true;
235: } catch (Exception ex) {
236: doLogError();
237: ex.printStackTrace();
238: customFile = false;
239: }
240: }
241: if (!customFile) {
242: try {
243: debugProperties.load(Debug.class
244: .getResourceAsStream(DEBUG_PROPERTIES));
245: } catch (Exception ex) {
246: doLogError();
247: ex.printStackTrace();
248: }
249: }
250: Object o = System.getProperty(DEFAULT_DEBUG_LEVEL_PROPERTY);
251: if (o != null) {
252: try {
253: int level = Integer.parseInt(o.toString());
254: debugProperties.put(DEFAULT_DEBUG_LEVEL_PROPERTY, o);
255: } catch (NumberFormatException nafta) {
256: System.err
257: .println("improper value for defaultDebugLevel: "
258: + o);
259: }
260: }
261: }
262:
263: private static void doWarnings(PrintWriter out, SQLWarning sw) {
264: do {
265: sw.printStackTrace(out);
266: } while ((sw = sw.getNextWarning()) != null);
267: }
268:
269: private static void doWarnings(PrintStream out, SQLWarning sw) {
270: do {
271: sw.printStackTrace(out);
272: } while ((sw = sw.getNextWarning()) != null);
273: }
274:
275: private static void doSQLExceptions(PrintWriter out, SQLException se) {
276: do {
277: se.printStackTrace(out);
278: } while ((se = se.getNextException()) != null);
279: }
280:
281: private static void doSQLExceptions(PrintStream out, SQLException se) {
282: do {
283: se.printStackTrace(out);
284: } while ((se = se.getNextException()) != null);
285: }
286:
287: private static void doLogError() {
288: System.err.println("ERROR IN " + getPackage(Debug.class) + "."
289: + DEBUG_PROPERTIES + "!");
290: }
291:
292: public static void main(String[] args) {
293: if (args.length > 0 && args[0].equals("refresh"))
294: Debug.initProperties();
295: }
296:
297: private Debug() {
298: //not meant to be instantiated
299: }
300:
301: }
302:
303: class DebugPriority implements Serializable {
304: public static final DebugPriority DP0 = new DebugPriority(0);
305: public static final DebugPriority DP1 = new DebugPriority(1);
306: public static final DebugPriority DP2 = new DebugPriority(2);
307: public static final DebugPriority DP3 = new DebugPriority(3);
308: public static final DebugPriority DP4 = new DebugPriority(4);
309: public static final DebugPriority DP5 = new DebugPriority(5);
310: public static final DebugPriority DP6 = new DebugPriority(6);
311: public static final DebugPriority DP7 = new DebugPriority(7);
312: public static final DebugPriority DP8 = new DebugPriority(8);
313: public static final DebugPriority DP9 = new DebugPriority(9);
314:
315: int priority;
316:
317: protected DebugPriority(int priority) {
318: this .priority = priority;
319: }
320:
321: public int getPriority() {
322: return priority;
323: }
324:
325: public String toString() {
326: return new StringBuffer("Debug Priority [").append(priority)
327: .append("]").toString();
328: }
329: }
|