Loggers and the LoggingMultiplexer
Loggers implement the "where" in logging, i.e., a Logger implements a specific destination for event logging. In Toothpick, all Loggers are subclasses of the class Logger. There are a number of destinations that events can be sent to:
- File - the standard Logger logs events to an external file.
- Transcript - during development, it is useful to log events to the Transcript.
- Windows Event Log - this logger logs to the OS event stream. You can then use Windows tools to track the output.
- Sockets - log to socket listeners such as the Unix syslogd
- Users - send event notification to users logged into the network
Defining a Logger
In order to function properly, a Logger needs to be aware of the other aspects of logging, namely the "whether" and the "how". You define a Logger by providing it with a LoggingPolicy and a LoggingFormatter. As an example, let's once again take a look at this code from the Quick Start:
| logger1 logger2 | logger1 := TranscriptLogger new format: SimpleLoggingFormatter defaultFormat; policy: (LoggingPolicy category: #debug level: #debug)). logger2 := FileLogger new fileName: 'MyLog.txt'; format: SimpleLoggingFormatter defaultFormat; policy: (LoggingPolicy category: #myapp level: #info).
Logger1 logs to the Transcript. In order to do its' job properly, we've supplied it with a Formatter and a Policy. Logger2 logs to a file, and because of that, we additionally need to supply it with a file name.
Once we've defined and configured a Logger, we need to set it up to actually be sent events. We do this by registering it with the LoggingMultiplexer singleton. This object serves as the central point that all events are sent to.After registering your logger, and telling the LoggingMultiplexer to start logging, you can forget about it. If you need to access your Logger directly, though, you can give it a name, and then access it via
LoggingMultiplexer current loggerNamed: 'my logger name'
The following code shows how to define our two Loggers, provide them with a name, register them with the LoggingMultiplexer, and start them logging.
| logger1 logger2 | logger1 := TranscriptLogger new name: 'My Transcript Logger'; format: SimpleLoggingFormatter defaultFormat; policy: (LoggingPolicy category: #debug level: #debug)). logger2 := FileLogger new name: 'My File Logger'; fileName: 'MyLog.txt'; format: SimpleLoggingFormatter defaultFormat; policy: (LoggingPolicy category: #myapp level: #info).
(LoggingMultiplexer current) addLogger: logger1; addLogger: logger2; startAllLoggers.
Logger has the following instVars:
|format||<LoggingFormat>||The formatter for outputting log events|
|name||<String>||The name of the outputter|
|stream||<Stream>||The output stream|
|isLogging||<Boolean>||Am I currently logging?|
|policy||<LoggingPolicy>||My logging policy|
The various subclasses add instance variables as required. For example, the FileLogger holds the file name in an instVar.
Published Thursday, October 19, 2006