如何提供诸如数据库,logging器等依赖关系到底层库?

build立

我正在为分布式应用程序构build基础库。 结构如下:

core_project/ lib/ index.js module1.js module2.js ... package.json 

我的应用程序的许多其他部分将使用这样的库:

 consumer_project/ node_modules/ core_project/ ... app.js package.json 

问题

我想要一些常见的依赖关系,比如消费者应用程序提供的DB处理程序。 一旦初始化,我希望所有的核心应用程序模块能够使用这些依赖关系。

尝试解决scheme

我试图在每个核心应用程序模块中创build一个模块初始化函数: core_project / lib / module1.js

 var cfg = {db: null}; module.exports = { // ... 'initModule': function (db) { cfg.db = db; } } 

这是我的核心模块索引文件: core_project / lib / index.js

 var modules = { 'module1': require('./module1'), 'module1': require('./module2'), // ... }; function create(db) { var app = {}; init(app, modules, db); return app; } function init(app, mods, db) { var m; for (m in mods) { if (mods.hasOwnProperty(m)) { if (mods[m].hasOwnProperty('initModule')) { mods[m].initModule(db); } app[m] = mods[m]; } } } module.exports = create; 

现在,我的消费者应用程序可以像这样传递依赖关系: consumer_project / app.js

 var core = require('core_project'); var db = // initialize db var app = core(db); // Start using app.module1.run(); 

尝试解决scheme的问题

  1. 我必须添加cfg = {db: null}并将initModule函数导出到每个需要依赖关系的模块中。
  2. 我必须将每个模块附加到core_project / lib / index.js中的核心应用程序对象

有没有更好的方式提供消费者提供的依赖关系,如数据库,logging到核心库及其所有模块?

传递依赖作为参数(即dependency injection)是一个完美的有效的方法来实现这一点,虽然你可以简化你的init使用闭包:

core_project / lib / module1.js

 module.exports = function(db) { return function() { // closure scoped with dependencies // can use db object }; } 

然后你的init函数会创build闭包:

 app[m] = mods[m](db); 

像这样传递代价通常是数据库客户端所希望的,因此在整个模块中使用相同的连接,但是其他types的代码logging器可能会更好地使用模块系统的标准require()方法导入,例如require('winston')