MongoDB
 sql >> Datenbank >  >> NoSQL >> MongoDB

Wie verschachtele ich ein Versprechen in einer anderen Versprechenfunktion in node.js?

Umgeben Sie das Ganze von einem new Promise anrufen hilft nichts. Darin hättest du immer noch die Callback-Hölle. Und nein, Promise.resolve() werfen bei einer Funktion, die nichts zurückgibt, hilft auch nichts.

Sie müssen versprechen die asynchronen Primitive, d. h. die kleinsten Teile, die asynchron sind. In Ihrem Fall ist das distance.matrix und Mongos connect +insert :

function getMatrix(m, o, d) {
    return new Promise(function(resolve, reject) {
        m.matrix(o, d, function(err, distances) {
            if (err) reject(err);
            else     resolve(distances);
        });
    });
}

function save(url, store, k) {
// cramming connect+insert in here is not optimal but let's not get into unnecessary detail
    return new Promise(function(resolve, reject) {
        MongoClient.connect(url, function(err, db) {
            if (err)
                reject(err);
            else
                db.collection(k).insert(store, function(err, results) {
                    if (err) reject(err);
                    else     resolve(results);
                    db.close();
                });
        });
    });
}

Jetzt, da wir diese haben, können wir sie tatsächlich nutzen und unsere Versprechen zu dem kombinieren, wonach Sie tatsächlich suchen:

module.exports = Promise.all(dep.map(function(name) {
    distance.departure_time(name);
    return getMatrix(distance, origins, destinations).then(function(distances) {
        if (!distances) throw new Error('no distances');
        var promises = [];
        if (distances.status == 'OK') {
            for (var i=0; i < origins.length; i++) {
                for (var j = 0; j < destinations.length; j++) {
                    var origin = distances.origin_addresses[i];
                    var destination = distances.destination_addresses[j];
                    if (distances.rows[0].elements[j].status == 'OK') {
                        var duration = distances.rows[i].elements[j].duration_in_traffic.value;
                        var myobj = {
                            destination: destination,
                            departure_time: name,
                            duration: duration
                        };
                        var str = destination.replace(/[,\s]+/g, '');
                        promises.push(save(url, myobj, str));
//                                    ^^^^^^^^^^^^^^^^^^^^^
                    }
                }
            }
        }
        return Promise.all(promises); // now wait for all save results
    });
}));