2012-12-07 52 views
13

我正在使用幾十個模塊和使用bunyan進行日誌記錄(JSON輸出,多個可配置流)的node.js應用程序。我一直在尋找關於如何在所有模塊中實現實例的很好的例子,但沒有看到似乎是我可以學習的一個非常乾淨的例子。通用日誌節點,快速應用 - 最佳實踐?

下面舉例說明了一種可行的方法,但對我來說似乎相當不雅(醜陋)。一般來說,我是新增節點& commonjs javascript,因此尋找有關如何改進它的建議。

模塊:./lib/logger

// load config file (would like this to be passed in to the constructor) 
nconf.file({ file: fileConfig}); 
var logSetting = nconf.get('log'); 

// instantiate the logger 
var Bunyan = require('bunyan'); 
var log = new Bunyan({ 
    name: logSetting.name, 
streams : [ 
     { stream : process.stdout, 
     level : logSetting.stdoutLevel}, 
     { path : logSetting.logfile, 
      level : logSetting.logfileLevel} 
    ], 
serializers : Bunyan.stdSerializers 
}); 

function Logger() { 
}; 

Logger.prototype.info = function info(e) { log.info(e) }; 
Logger.prototype.debug = function debug(e) { log.debug(e) }; 
Logger.prototype.trace = function trace(e) { log.trace(e) }; 
Logger.prototype.error = function error(e) { log.error(e) }; 
Logger.prototype.warn = function warn(e) { log.warn(e) }; 

module.exports = Logger; 

模塊:主要應用

// create the logger 
var logger = require('./lib/logger) 
var log = new logger(); 

// note: would like to pass in options --> new logger(options) 


module: any project module using logger 
// open the logger (new, rely on singleton...) 
var logger = require('./lib/logger'); 
var log = new logger(); 

view the gist

任何建議?

編輯:

我修改的構造,使得單件模式明確的(而不是隱含的「要求」行爲的一部分

var log = null; 
function Logger(option) { 

// make the singleton pattern explicit 
if (!Logger.log) { 
    Logger.log = this; 
} 
    return Logger.log; 
}; 

,然後改變了初始化採取選項參數

// initialize the logger 
Logger.prototype.init = function init(options) { 
log = new Bunyan({ 
    name: options.name, 
    streams : [ 
     { stream : process.stdout, 
      level : options.stdoutLevel}, 
     { path : options.logfile, 
      level : options.logfileLevel} 
    ], 
    serializers : Bunyan.stdSerializers  
    }); 
}; 
+0

你有什麼看起來像一個基本的單使用require的功能構建。你可以實現你自己的單身人士,但它不一定會更好。也許可以完成依賴注入? – mtsr

+0

感謝您的答覆 - 是的,這是一個基本的單身人士。 (a)單例行爲是隱含的,而不是顯式的,(b)我還沒有找到一個乾淨的方式讓構造函數接受參數(比如選項JSON),而不必確定是否它們已經被前一個模塊加載,並且(c)將參考(作爲參數)傳遞給每個單個模塊的替代方案看起來雜亂/冗長。 – dewd

+0

感謝您的回覆!是的,這是一個基本的單身人士,雖然它似乎是一種隱含的行爲,而不是一個明確的行爲。我看了[壞習慣?](http://stackoverflow.com/questions/9733201/is-it-a-bad-practice-to-use-the-requirejs-module-as-a-singleton), [單身模式](http://jasonwyatt.tumblr.com/post/8087061585/singleton-pattern-with-requirejs)加[使用單身需求](http://stackoverflow.com/questions/5608685/using-requirejs如何在全局對象或單例中繞過),它們似乎更好地解決了構造函數的行爲。 – dewd

回答

1

,如果你使用的是表達對Node.js的,那麼你可以試試這個。 默認情況下,日誌記錄在快遞你。禁用必須做某些事情來獲取適用於您的應用程序的日誌。對於訪問日誌,我們需要使用Logger中間件;對於錯誤日誌,我們將使用Forever.Hope它會幫助你.. 這裏是一個很好的例子How to Logging Access及差錯的node.js

+1

謝謝,這是一個有用的參考。我已經使用了類似的模式來使用Bunyan的快速日誌記錄中間件,我在那裏掙扎的是創建一個乾淨的包裝類,它允許我在所有模塊中使用相同的實例,並且允許傳入選項的初始化方法。將發佈我想出來的... – dewd

23

Singleton pattern in nodejs - is it needed? 其實,也許並不需要節點的環境下單。所有你需要做的是在一個單獨的文件中創建一個記錄說,logger.js:

 
var bunyan = require("bunyan"); // Bunyan dependency 
var logger = bunyan.createLogger({name: "myLogger"}); 

module.exports = logger; 

然後,從另一模塊該記錄器:

 
var logger = require("./logger"); 
logger.info("Anything you like"); 
+0

我喜歡這種方法,但是如何在首次使用之前配置記錄器?我想用這種方式,但我想設置輸出路徑。我試圖在logger.js中包含「init」函數並在其中設置「module.exports」,但它不好。 –

+0

@lixiang這是否會在每次需要時創建一個新的記錄器實例? – PixMach

+1

@PixMach,不,需求模塊會緩存對象實例 – lixiang