javascript - node.js ~ constructing chained sequence of Promise resolves -


can suggest better way structure use of promises? i'm newish promises , wondering if i'm missing how construct chain of events.

note: intention not use rej[ect] here. see guatanrees res[olve] returns. meaning code returns needs 1 path handle returned value. thereby code returned simplier in it's flow.

it might know, if don't recognize it, taken module created. think of dao.

module.exports = {      dbconnection: function () {         return { user: 'sa', password: 'mypassword', server: 'localhost', database: 'mydb' };     },       caniconnecttothedb: function () {         return new promise(function (res, rej) {             var sql = require('mssql');             var mydao = require('./mydao');             var cn = new sql.connectionpool(mydao.dbconnection());              cn.connect().then(function () {                 var req = new sql.request(cn);                 var qry = 'select serverproperty(\'productversion\') \'rs\'';                 req.query(qry)                     .then(function (rs) {                         qry = 'select isnull(object_id(\'someobjectiknowexists\'), -1)';                         req.query(qry)                             .then(function (rss) {                                 res(' connected// master db success// db success');                             })                             .catch(function (err) {                                 res(' connected// master db success// issue querying db //' + err + '//');                             });                     })                     .catch(function (er) {                         res(' connected// not query master db //' + er + '//');                     });             })             .catch(function () {                 res(' can not connect');             });         });     } }; 

the key thing remember promises then returns new promise (as catch). how new promise settled depends on return handler: if return promise, new promise then/catch slaved 1 returned; if return value, new promise resolved value.

so can chain them together. think of then , catch handlers transforming filters ultimate result flows through.

note if have starting point gives promise (cn.connect()), don't need new promise: use then , catch transform passes through chain returning (new) resolution value.

another key thing remember if catch handler returns value, converts rejection resolution. continue down rejection path, catch handler must either throw exception or return promise is/will rejected.

finally: require calls should @ beginning of module.

so, without removing conversion of rejections resolutions (more on in moment):

var sql = require('mssql'); var mydao = require('./mydao');  module.exports = {      dbconnection: function () {         return { user: 'sa', password: 'mypassword', server: 'localhost', database: 'mydb' };     },       caniconnecttothedb: function () {         var cn = new sql.connectionpool(mydao.dbconnection());         return cn.connect()             .then(function () {                 var req = new sql.request(cn);                 var qry = 'select serverproperty(\'productversion\') \'rs\'';                 return req.query(qry)                     .then(function (rs) {                         qry = 'select isnull(object_id(\'someobjectiknowexists\'), -1)';                         return req.query(qry)                             .then(function (rss) { // note you're not using rss anywhere                                 return ' connected// master db success// db success';                             })                             .catch(function (err) {                                 return ' connected// master db success// issue querying db //' + err + '//';                             });                     })                     .catch(function (er) {                         return ' connected// not query master db //' + er + '//';                     });             })             .catch(function() {                 return ' can not connect';             });     } }; 

note: intention not use rej[ect] here. see guatanrees res[olve] returns. meaning code returns needs 1 path handle returned value. thereby code returned simplier in it's flow.

rejections follow separate path resolutions reason. doesn't make things more complicated, makes things simpler. don't convert rejections resolutions unless you're done error-recovery of kind , can continue on though rejection hadn't happened.

here's code rejections allowed rejections:

var sql = require('mssql'); var mydao = require('./mydao');  module.exports = {      dbconnection: function () {         return { user: 'sa', password: 'mypassword', server: 'localhost', database: 'mydb' };     },      caniconnecttothedb: function () {         var cn = new sql.connectionpool(mydao.dbconnection());         return cn.connect()             .then(function () {                 var req = new sql.request(cn);                 var qry = 'select serverproperty(\'productversion\') \'rs\'';                 return req.query(qry)                     .then(function (rs) {                         qry = 'select isnull(object_id(\'someobjectiknowexists\'), -1)';                         return req.query(qry)                             .then(function (rss) { // note you're not using rss anywhere                                 return ' connected// master db success// db success';                             });                     });             });     } }; 

using it:

themodule.caniconnecttothedb()     .then(function() {         // yes, let's     })     .catch(function() {         // no, report problem, etc.     }); 

i'd abstract out bit assume you'll end doing on , over: establishing connection , getting request object it:

var sql = require('mssql'); var mydao = require('./mydao');  function getrequest() {     var cn = new sql.connectionpool(mydao.dbconnection());     return cn.connect().then(function() {         return new sql.request(cn);     }); }  module.exports = {      dbconnection: function () {         return { user: 'sa', password: 'mypassword', server: 'localhost', database: 'mydb' };     },      caniconnecttothedb: function () {         return getrequest().then(function(req) {             var qry = 'select serverproperty(\'productversion\') \'rs\'';             return req.query(qry)                 .then(function (rs) {                     qry = 'select isnull(object_id(\'someobjectiknowexists\'), -1)';                     return req.query(qry)                         .then(function (rss) { // note you're not using rss anywhere                             return ' connected// master db success// db success';                         });                 });         });     } }; 

Comments