How to properly use Parse / Promise?

2019-09-17 03:41发布

问题:

I am writing some JavaScript codes using Parse.com.

To be honest, I have been reading how to use Promise and done lots of research but cannot still figure out how to use it properly..

Here is a scenario:

  1. I have two tables (objects) called Client and InvoiceHeader
  2. Client can have multiple InvoiceHeaders.
  3. InvoiceHeader has a column called "Amount" and I want a total amount of each client's InvoiceHeaders.

For example, if Client A has two InvoiceHeaders with amount 30 and 20 and Client B has got nothing, the result I want to see in tempArray is '50, 0'.

However, with the following codes, it looks like it's random. I mean sometimes the tempArray got '50, 50' or "50, 0". I suspect it is due to the wrong usage of Promise.

Please help me. I have been looking into the codes and stuck for a few days.

$(document).ready(function() {
    var client = Parse.Object.extend("Client");
    var query = new Parse.Query(client);
    var tempArray = [];

    query.find().then(function(objects) {
        return objects;
    }).then(function (objects) {
        var promises = [];
        var totalForHeader = 0;

        objects.forEach(function(object) {
            totalForHeader = 0;

            var invoiceHeader = Parse.Object.extend('InvoiceHeader');
            var queryForInvoiceHeader = new Parse.Query(invoiceHeader);
            queryForInvoiceHeader.equalTo('headerClient', object);

            var prom = queryForInvoiceHeader.find().then(function(headers) {

                headers.forEach(function(header) {
                    totalForHeader += totalForHeader +
                                      parseFloat(header.get('headerOutstandingAmount'));
                });

                tempArray.push(totalForHeader);
            });
            promises.push(prom);
        });
        return Parse.Promise.when.apply(Parse.Promise, promises);

    }).then(function () {
        // after all of above jobs are done, do something here...
    });
} );

回答1:

Assuming Parse.com's Promise class follows the A+ spec, and I understood which bits you wanted to end up where, this ought to work:

$(document).ready(function() {

    var clientClass = Parse.Object.extend("Client");
    var clientQuery = new Parse.Query(clientClass);

    clientQuery.find().then(function(clients) {

        var totalPromises = [];

        clients.forEach(function(client) {

            var invoiceHeaderClass = Parse.Object.extend('InvoiceHeader');
            var invoiceHeaderQuery = new Parse.Query(invoiceHeaderClass);
            invoiceHeaderQuery.equalTo('headerClient', client);

            var totalPromise = invoiceHeaderQuery.find().then(function(invoiceHeaders) {
                var totalForHeader = 0;
                invoiceHeaders.forEach(function(invoiceHeader) {
                    totalForHeader += parseFloat(invoiceHeader.get('headerOutstandingAmount'));
                });
                return totalForHeader;
            });

            totalPromises.push(totalPromise);

        });

        return Parse.Promise.when(totalPromises);

    }).then(function(totals) {

        // here you can use the `totals` array.

    });
});