diff --git a/README.md b/README.md index e613b0d..0d2c196 100644 --- a/README.md +++ b/README.md @@ -21,10 +21,10 @@ NOTE: from log4js 0.5 onwards you'll need to explicitly enable replacement of no ```javascript { - appenders: [ - { type: "console" } - ], - replaceConsole: true + appenders: [ + { type: "console" } + ], + replaceConsole: true } ``` @@ -42,9 +42,9 @@ var logger = log4js.getLogger(); logger.debug("Some debug messages"); ``` By default, log4js outputs to stdout with the coloured layout (thanks to [masylum](http://github.com/masylum)), so for the above you would see: - - [2010-01-17 11:43:37.987] [DEBUG] [default] - Some debug messages - +```bash +[2010-01-17 11:43:37.987] [DEBUG] [default] - Some debug messages +``` See example.js for a full example, but here's a snippet (also in fromreadme.js): ```javascript var log4js = require('log4js'); @@ -53,7 +53,7 @@ var log4js = require('log4js'); log4js.loadAppender('file'); //log4js.addAppender(log4js.appenders.console()); log4js.addAppender(log4js.appenders.file('logs/cheese.log'), 'cheese'); -```javascript + var logger = log4js.getLogger('cheese'); logger.setLevel('ERROR'); @@ -65,18 +65,18 @@ logger.error('Cheese is too ripe!'); logger.fatal('Cheese was breeding ground for listeria.'); ``` Output: - - [2010-01-17 11:43:37.987] [ERROR] cheese - Cheese is too ripe! - [2010-01-17 11:43:37.990] [FATAL] cheese - Cheese was breeding ground for listeria. - +```bash +[2010-01-17 11:43:37.987] [ERROR] cheese - Cheese is too ripe! +[2010-01-17 11:43:37.990] [FATAL] cheese - Cheese was breeding ground for listeria. +``` The first 5 lines of the code above could also be written as: ```javascript var log4js = require('log4js'); log4js.configure({ - appenders: [ - { type: 'console' }, - { type: 'file', filename: 'logs/cheese.log', category: 'cheese' } - ] + appenders: [ + { type: 'console' }, + { type: 'file', filename: 'logs/cheese.log', category: 'cheese' } + ] }); ``` @@ -106,28 +106,28 @@ For FileAppender you can also pass the path to the log directory as an option wh log4js.configure('my_log4js_configuration.json', { cwd: '/absolute/path/to/log/dir' }); ``` If you have already defined an absolute path for one of the FileAppenders in the configuration file, you could add a "absolute": true to the particular FileAppender to override the cwd option passed. Here is an example configuration file: - - #### my_log4js_configuration.json #### +```json +#### my_log4js_configuration.json #### +{ + "appenders": [ { - "appenders": [ - { - "type": "file", - "filename": "relative/path/to/log_file.log", - "maxLogSize": 20480, - "backups": 3, - "category": "relative-logger" - }, - { - "type": "file", - "absolute": true, - "filename": "/absolute/path/to/log_file.log", - "maxLogSize": 20480, - "backups": 10, - "category": "absolute-logger" - } - ] + "type": "file", + "filename": "relative/path/to/log_file.log", + "maxLogSize": 20480, + "backups": 3, + "category": "relative-logger" + }, + { + "type": "file", + "absolute": true, + "filename": "/absolute/path/to/log_file.log", + "maxLogSize": 20480, + "backups": 10, + "category": "absolute-logger" } - + ] +} +``` Documentation for most of the core appenders can be found on the [wiki](log4js-node/wiki/Appenders), otherwise take a look at the tests and the examples. ## Documentation diff --git a/example-connect-logger.js b/examples/example-connect-logger.js similarity index 100% rename from example-connect-logger.js rename to examples/example-connect-logger.js diff --git a/example-socket.js b/examples/example-socket.js similarity index 100% rename from example-socket.js rename to examples/example-socket.js diff --git a/example.js b/examples/example.js similarity index 100% rename from example.js rename to examples/example.js diff --git a/fromreadme.js b/examples/fromreadme.js similarity index 100% rename from fromreadme.js rename to examples/fromreadme.js diff --git a/log-rolling.js b/examples/log-rolling.js similarity index 100% rename from log-rolling.js rename to examples/log-rolling.js diff --git a/memory-test.js b/examples/memory-test.js similarity index 100% rename from memory-test.js rename to examples/memory-test.js diff --git a/examples/patternLayout-tokens.js b/examples/patternLayout-tokens.js new file mode 100644 index 0000000..84b171c --- /dev/null +++ b/examples/patternLayout-tokens.js @@ -0,0 +1,21 @@ +var log4js = require('./lib/log4js'); + +var config = { + "appenders": [ + { + "type": "console", + "layout": { + "type": "pattern", + "pattern": "%[%r (%x{pid}) %p %c -%] %m%n", + "tokens": { + "pid" : function() { return process.pid; } + } + } + } + ] + }; + +log4js.configure(config, {}); + +var logger = log4js.getLogger("app"); +logger.info("Test log message"); \ No newline at end of file diff --git a/lib/appenders/multiprocess.js b/lib/appenders/multiprocess.js index 9ab7bc9..a698097 100644 --- a/lib/appenders/multiprocess.js +++ b/lib/appenders/multiprocess.js @@ -115,11 +115,11 @@ function createAppender(config) { } } -function configure(config) { +function configure(config, options) { var actualAppender; if (config.appender && config.mode === 'master') { log4js.loadAppender(config.appender.type); - actualAppender = log4js.appenderMakers[config.appender.type](config.appender); + actualAppender = log4js.appenderMakers[config.appender.type](config.appender, options); config.actualAppender = actualAppender; } return createAppender(config); diff --git a/lib/layouts.js b/lib/layouts.js index c0a8cc2..a8ae55a 100644 --- a/lib/layouts.js +++ b/lib/layouts.js @@ -10,8 +10,9 @@ var dateFormat = require('./date_format') , "coloured": function() { return colouredLayout; } , "pattern": function (config) { var pattern = config.pattern || undefined; - return patternLayout(pattern); - } + var tokens = config.tokens || undefined; + return patternLayout(pattern, tokens); + } } , colours = { ALL: "grey" @@ -121,13 +122,26 @@ function messagePassThroughLayout (loggingEvent) { * - %d date in various formats * - %% % * - %n newline + * - %x{} add dynamic tokens to your log. Tokens are specified in the tokens parameter * You can use %[ and %] to define a colored block. - * Takes a pattern string and returns a layout function. + * + * Tokens are specified as simple key:value objects. + * The key represents the token name whereas the value can be a string or function + * which is called to extract the value to put in the log message. If token is not + * found, it doesn't replace the field. + * + * A sample token would be: { "pid" : function() { return process.pid; } } + * + * Takes a pattern string, array of tokens and returns a layout function. + * @param {String} Log format pattern String + * @param {object} map object of different tokens + * @return {Function} * @author Stephan Strittmatter + * @author Jan Schmidle */ -function patternLayout (pattern) { +function patternLayout (pattern, tokens) { var TTCC_CONVERSION_PATTERN = "%r %p %c - %m%n"; - var regex = /%(-?[0-9]+)?(\.?[0-9]+)?([\[\]cdmnpr%])(\{([^\}]+)\})?|([^%]+)/; + var regex = /%(-?[0-9]+)?(\.?[0-9]+)?([\[\]cdmnprx%])(\{([^\}]+)\})?|([^%]+)/; pattern = pattern || TTCC_CONVERSION_PATTERN; @@ -203,6 +217,17 @@ function patternLayout (pattern) { case "%": replacement = "%"; break; + case "x": + if(typeof(tokens[specifier]) !== 'undefined') { + if(typeof(tokens[specifier]) === 'function') { + replacement = tokens[specifier](); + } else { + replacement = tokens[specifier]; + } + } else { + replacement = matchedString; + } + break; default: replacement = matchedString; break; diff --git a/lib/streams/BufferedWriteStream.js b/lib/streams/BufferedWriteStream.js index d10c8c7..6820c82 100644 --- a/lib/streams/BufferedWriteStream.js +++ b/lib/streams/BufferedWriteStream.js @@ -1,4 +1,5 @@ var events = require('events'), + Dequeue = require('dequeue'), util = require('util'); module.exports = BufferedWriteStream; @@ -6,7 +7,7 @@ module.exports = BufferedWriteStream; function BufferedWriteStream(stream) { var that = this; this.stream = stream; - this.buffer = []; + this.buffer = new Dequeue(); this.canWrite = false; this.bytes = 0; diff --git a/package.json b/package.json index 44a12ad..6476613 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "log4js", - "version": "0.5.6", + "version": "0.5.7", "description": "Port of Log4js to work with node.", "keywords": [ "logging", @@ -26,7 +26,8 @@ "lib": "lib" }, "dependencies": { - "async": "0.1.15" + "async": "0.1.15", + "dequeue": "1.0.3" }, "devDependencies": { "vows": "0.6.2", diff --git a/test/layouts-test.js b/test/layouts-test.js index 26a3786..c32f103 100644 --- a/test/layouts-test.js +++ b/test/layouts-test.js @@ -4,9 +4,10 @@ assert = require('assert'); //used for patternLayout tests. function test(args, pattern, value) { var layout = args[0] - , event = args[1]; + , event = args[1] + , tokens = args[2]; - assert.equal(layout(pattern)(event), value); + assert.equal(layout(pattern, tokens)(event), value); } vows.describe('log4js layouts').addBatch({ @@ -174,8 +175,12 @@ vows.describe('log4js layouts').addBatch({ level: { toString: function() { return "DEBUG"; } } - }, layout = require('../lib/layouts').patternLayout; - return [layout, event]; + }, layout = require('../lib/layouts').patternLayout + , tokens = { + testString: 'testStringToken', + testFunction: function() { return 'testFunctionToken'; } + }; + return [layout, event, tokens]; }, 'should default to "time logLevel loggerName - message"': function(args) { @@ -245,6 +250,18 @@ vows.describe('log4js layouts').addBatch({ }, '%[%r%] should output colored time': function(args) { test(args, '%[%r%]', '\033[36m14:18:30\033[39m'); - } + }, + '%x{testString} should output the string stored in tokens': function(args) { + test(args, '%x{testString}', 'testStringToken'); + }, + '%x{testFunction} should output the result of the function stored in tokens': function(args) { + test(args, '%x{testFunction}', 'testFunctionToken'); + }, + '%x{doesNotExist} should output the string stored in tokens': function(args) { + test(args, '%x{doesNotExist}', '%x{doesNotExist}'); + }, + '%x should output the string stored in tokens': function(args) { + test(args, '%x', '%x'); + }, } }).export(module);