NodeJS Express Inyección de dependencia y conexiones de base de datos

Proveniente de un fondo que no pertenece al Nodo, mi primer instinto es definir mi servicio como tal

MyService.js module.exports = new function(dbConnection) { // service uses the db } 

Ahora, quiero una conexión de base de datos abierta por solicitud, así que defino en middleware:

 res.locals.db = openDbConnection(); 

Y en algunos códigos api Express de consumo:

 api.js var MyService = require(./services/MyService') ... router.get('/foo/:id?', function (req, res) { var service = new MyService(res.locals.db); }); 

Ahora, dado que el método preferido de dependency injection de Node es a través de la statement de require(...) , parece que no debería usar el constructor de MyService para la inyección de la db .

Así que digamos que quiero tener

 var db = require('db'); 

en la parte superior de MyService y luego uso de alguna manera como db.current …. pero ¿cómo ataría el db al objeto res.locals actual ahora que db es un módulo en sí mismo? ¿Cuál es una forma recomendada de manejar este tipo de thin en Node?

Respuesta actualizada: 02/05/15

Si desea adjuntar una conexión de base de datos a cada objeto de solicitud, luego use esa conexión en su servicio, la conexión tendrá que ser transferida a myService alguna manera. El siguiente ejemplo muestra una forma de hacerlo. Si intentamos usar db.current o algo parecido, estaremos almacenando el estado en nuestro módulo DB. En mi experiencia, eso llevará a problemas.

Alternativamente, expongo el enfoque que he usado (y sigo usando) en esta respuesta anterior . Lo que esto significa para este ejemplo es lo siguiente:

 // api.js var MyService = require(./services/MyService') ... router.get('/foo/:id?', function (req, res) { MyService.performTask(req.params.id); }); // MyService.js var db = require('db'); module.exports = { performTask: function(id) { var connection = db.getOpenConnection(); // Do whatever you want with the connection. } } 

Con este enfoque, hemos desacoplado el módulo DB de los módulos api / app / router y solo el módulo que realmente lo usa sabrá que existe.

Respuesta anterior: 01/05/15

Lo que estás hablando podría hacerse usando un middleware expreso. Esto es lo que podría parecer:

 var db = require('db'); // Attach a DB connection to each request coming in router.use(req, res, next){ req.locals.db = db.getOpenConnection(); next(); } // Later on.. router.get('/foo/:id?', function (req, res) { // We should now have something attached to res.locals.db! var service = new MyService(res.locals.db); }); 

Personalmente nunca había visto algo así como el new MyService en aplicaciones Express. Eso no significa que no se pueda hacer, pero podría considerar un enfoque como este

 // router.js var MyService = require('MyService'); router.get('/foo/:id?', function (req, res) { MyService.foo(res.locals.db); }); // MyService.js module.exports.foo(connection){ // I have a connection! } 
Intereting Posts