/* Wotonomy: OpenStep design patterns for pure Java applications. Copyright (C) 2001 Intersect Software Corporation This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, see http://www.gnu.org */ package net.wotonomy.foundation; import java.io.ByteArrayOutputStream; import java.io.FileOutputStream; import java.io.PrintStream; import java.util.Date; /** * NSLog is foundation's built-in logging facility: IMPLEMENTED, BUT NOT TESTED. * By default, all groups are enabled, and debug level is DebugLevelOff. * * @author michael@mpowers.net * @author $Author: cgruber $ * @version $Revision: 893 $ */ public class NSLog { public static long DebugGroupApplicationGeneration = 1L << 3; public static long DebugGroupArchiving = 1L << 6; public static long DebugGroupAssociations = 1L << 19; public static long DebugGroupComponentBindings = 1L << 9; public static long DebugGroupControllers = 1L << 20; public static long DebugGroupComponents = 1L << 26; public static long DebugGroupDatabaseAccess = 1L << 16; public static long DebugGroupDeployment = 1L << 22; public static long DebugGroupEnterpriseObjects = 1L << 1; public static long DebugGroupFormatting = 1L << 10; public static long DebugGroupIO = 1L << 13; public static long DebugGroupJSPServlets = 1L << 27; public static long DebugGroupKeyValueCoding = 1L << 8; public static long DebugGroupModel = 1L << 15; public static long DebugGroupMultithreading = 1L << 4; public static long DebugGroupParsing = 1L << 23; public static long DebugGroupQualifiers = 1L << 11; public static long DebugGroupReflection = 1L << 24; public static long DebugGroupRequestHandling = 1L << 25; public static long DebugGroupResources = 1L << 5; public static long DebugGroupRules = 1L << 21; public static long DebugGroupSQLGeneration = 1L << 17; public static long DebugGroupTiming = 1L << 14; public static long DebugGroupUserInterface = 1L << 18; public static long DebugGroupValidation = 1L << 7; public static long DebugGroupWebObjects = 1L << 2; public static long DebugGroupWebServices = 1L << 2; public static int DebugLevelOff = 0; public static int DebugLevelCritical = 1; public static int DebugLevelInformational = 2; public static int DebugLevelDetailed = 3; /** * The logger to which debug statements should be * conditionally written. By default, these messages * appear on the standard error stream. */ public static Logger debug; /** * The logger to which error messages should be written, * which may not always be user-visible. By default, * these messages appear on the standard error stream. */ public static Logger err; /** * The logger to which user-visible messages should be written. * By default, these messages appear on the standard output stream. */ public static Logger out; private static long allowedGroups; private static int allowedLevel; static { debug = new PrintStreamLogger( System.err ); err = new PrintStreamLogger( System.err ); out = new PrintStreamLogger( System.out ); //TODO: need to initialize the debug level and groups based // on the value of the NSDebugLevel and NSDebugGroup properties allowedGroups = Long.MAX_VALUE; allowedLevel = 0; } /** * Adds the specified group masks to those allowed for logging. */ public static void allowDebugLoggingForGroups(long aDebugGroups) { allowedGroups = allowedGroups | aDebugGroups; } /** * Returns the current logging debug level. */ public static int allowedDebugLevel() { return allowedLevel; } /** * Returns whether logging is allowed for the specified groups masks. */ public static boolean debugLoggingAllowedForGroups(long aDebugGroups) { return ( allowedGroups == ( allowedGroups | aDebugGroups ) ); } /** * Returns whether logging is allowed for the specified level. */ public static boolean debugLoggingAllowedForLevel(int aDebugLevel) { return ( allowedLevel >= aDebugLevel ); } /** * Returns whether logging allowed for the specified groups masks * at the specified level. Convenience method. */ public static boolean debugLoggingAllowedForLevelAndGroups(int aDebugLevel, long aDebugGroups) { return ( ( allowedLevel >= aDebugLevel ) && ( allowedGroups == ( allowedGroups | aDebugGroups ) ) ); } /** * Convenience to obtain a java PrintStream for the specified file path. * Returns null if the stream could not be created. */ public static PrintStream printStreamForPath(String aPath) { try { return new PrintStream( new FileOutputStream( aPath ) ); } catch ( Throwable t ) { } return null; } /** * Removes the specified group masks from those allowed for logging. */ public static void refuseDebugLoggingForGroups(long aDebugGroups) { allowedGroups = ( allowedGroups | aDebugGroups ) ^ aDebugGroups; } /** * Sets the allowed groups to only those specified by the mask. */ public static void setAllowedDebugGroups(long aDebugGroups) { allowedGroups = aDebugGroups; } /** * Sets the current debug level. */ public static void setAllowedDebugLevel(int aDebugLevel) { allowedLevel = aDebugLevel; } /** * Sets the current debug logger. * Does nothing if logger is null. */ public static void setDebug(NSLog.Logger logger) { if ( logger != null ) { debug = logger; } } /** * Sets the current error logger. * Does nothing if logger is null. */ public static void setErr(NSLog.Logger logger) { if ( logger != null ) { err = logger; } } /** * Sets the current output logger. * Does nothing if logger is null. */ public static void setOut(NSLog.Logger logger) { if ( logger != null ) { out = logger; } } /** * Convenience to write the throwable's stack trace * to a string. */ public static String throwableAsString(Throwable t) { ByteArrayOutputStream os = new ByteArrayOutputStream(); PrintStream ps = new PrintStream( os ); t.printStackTrace( ps ); return os.toString(); } /** * The abstract superclass of all Logger implementations. */ static abstract public class Logger { private boolean enabled; private boolean verbose; /** * Default constructor sets enabled * and verbose to true. */ public Logger() { enabled = true; verbose = true; } /** * Convenience to append a Boolean. */ public void appendln(boolean aValue) { appendln( new Boolean( aValue ) ); } /** * Convenience to append a Byte. */ public void appendln(byte aValue) { appendln( new Byte( aValue ) ); } /** * Convenience to write a String * comprised of the byte array using * the default encoding. */ public void appendln(byte[] aValue) { appendln( new String( aValue ) ); } /** * Convenience to append a Character. */ public void appendln(char aValue) { appendln( new Character( aValue ) ); } /** * Convenience to append a String * comprised of the character array. */ public void appendln(char[] aValue) { appendln( new String( aValue ) ); } /** * Convenience to append a Double. */ public void appendln(double aValue) { appendln( new Double( aValue ) ); } /** * Convenience to append a Float. */ public void appendln(float aValue) { appendln( new Float( aValue ) ); } /** * Convenience to append a Integer. */ public void appendln(int aValue) { appendln( new Integer( aValue ) ); } /** * Convenience to append a Long. */ public void appendln(long aValue) { appendln( new Long( aValue ) ); } /** * Convenience to append a Short */ public void appendln(short aValue) { appendln( new Short( aValue ) ); } /** * Convenience to append a Throwable. */ public void appendln(Throwable aValue) { appendln( NSLog.throwableAsString( aValue ) ); } /** * Writes the object to the log. */ public abstract void appendln(Object aValue); /** * Appends a line to the log. */ public abstract void appendln(); /** * Flushes any buffered output to the log. */ public abstract void flush(); /** * Returns whether the logger is enabled, * the meaning of which is defined by the * implementing class. */ public boolean isEnabled() { return enabled; } /** * Returns whether the logger is verbose, * the meaning of which is defined by the * implementing class. */ public boolean isVerbose() { return verbose; } /** * Sets whether the logger is enabled, * the meaning of which is defined by the * implementing class. */ public void setIsEnabled(boolean aBool) { enabled = aBool; } /** * Sets whether the logger is verbose, * the meaning of which is defined by the * implementing class. */ public void setIsVerbose(boolean aBool) { verbose = aBool; } } /** * The default implementation of Logger that writes to a Java * PrintStream. If not enabled, no output is written. * If verbose, output is in format: "[time] message". */ static public class PrintStreamLogger extends Logger { private PrintStream thePrintStream; /** * Constructor takes a PrintStream. */ public PrintStreamLogger(PrintStream ps) { thePrintStream = ps; } /** * Sends a newline to the print stream. */ public void appendln() { if ( isEnabled() ) { thePrintStream.println(); } } /** * Writes the throwable to the print stream. */ public void appendln(Throwable aValue) { appendln( NSLog.throwableAsString( aValue ) ); } /** * Writes aValue.toString to the print stream. */ public void appendln(Object aValue) { if ( isEnabled() ) { if ( isVerbose() ) { thePrintStream.print( '[' + new Date().toString() + "] <" + Thread.currentThread().getName() + "> " ); } if ( aValue == null ) aValue = "null"; thePrintStream.println( aValue.toString() ); } } /** * Flushes the print stream. */ public void flush() { thePrintStream.flush(); } /** * Returns the current print stream. */ public PrintStream printStream() { return thePrintStream; } /** * Replaces the current print stream. */ public void setPrintStream(PrintStream aStream) { thePrintStream = aStream; } } } /* * $Log$ * Revision 1.2 2006/02/16 13:15:00 cgruber * Check in all sources in eclipse-friendly maven-enabled packages. * * Revision 1.1 2003/01/31 22:33:00 mpowers * Contributing NSLog. * * */