2014-11-10 7 views
0

Я пишу работу, которую я хочу запускать каждый час в фоновом режиме на Parse. В моей базе данных есть две таблицы. Первый содержит список Question s, а во втором перечислены все пары user \ question agreement (QuestionAgreement s). Первоначально мой план состоял в том, чтобы клиент сам подсчитал QuestionAgreement, но я обнаружил, что это приводит к множеству запросов, которые действительно могут быть устранены, поэтому я хочу, чтобы это фоновое задание выполняло подсчет, а затем обновляло поле непосредственно на Question с ним.Кодирование парсера-кода досрочно?

Вот моя попытка:

Parse.Cloud.job("updateQuestionAgreementCounts", function(request, status) { 
    Parse.Cloud.useMasterKey(); 
    var query = new Parse.Query("Question"); 
    query.each(function(question) { 
     var agreementQuery = new Parse.Query("QuestionAgreement"); 
     agreementQuery.equalTo("question", question); 
     agreementQuery.count({ 
      success: function(count) { 
       question.set("agreementCount", count); 
       question.save(null, null); 
      } 
     }); 
    }).then(function() { 
     status.success("Finished updating Question Agreement Counts."); 
    }, function(error) { 
     status.error("Failed to update Question Agreement Counts.") 
    }); 
}); 

Проблема заключается в том, это только кажется, работает на несколько Question с, а затем он останавливается, появляется в разделе Статус работы на Разбор Dashboard как " удалось». Я подозреваю, что проблема в том, что она возвращается преждевременно. Вот мои вопросы:

1 - Как я могу удержать это от преждевременного возвращения? (Предполагая, что это, по сути, моя проблема.)

2 - Каков наилучший способ отладки кода облака? Поскольку это не клиентская сторона, у меня нет способа установить точки останова или что-то еще, не так ли?

ответ

0

Я смог использовать обещания, как предложил knshn, чтобы сделать его таким, чтобы мой код завершился до успешного выполнения.

Parse.Cloud.job("updateQuestionAgreementCounts", function(request, status) { 
    Parse.Cloud.useMasterKey(); 
    var promises = []; // Set up a list that will hold the promises being waited on. 
    var query = new Parse.Query("Question"); 
    query.each(function(question) { 
     var agreementQuery = new Parse.Query("QuestionAgreement"); 
     agreementQuery.equalTo("question", question); 
     agreementQuery.equalTo("agreement", 1); 

     // Make sure that the count finishes running first! 
     promises.push(agreementQuery.count().then(function(count) { 
      question.set("agreementCount", count); 

      // Make sure that the object is actually saved first! 
      promises.push(question.save(null, null)); 
     })); 
    }).then(function() { 
     // Before exiting, make sure all the promises have been fulfilled! 
     Parse.Promise.when(promises).then(function() { 
      status.success("Finished updating Question Agreement Counts."); 
     }); 
    }); 
}); 
1

status.success вызывается до завершения асинхронных вызовов успеха count. Чтобы предотвратить это, вы можете использовать обещания здесь. Проверьте документы для Parse.Query.each.

Итерации по каждому результату запроса, вызывающего обратный вызов для каждого из них. Если обратный вызов возвращает обещание, итерация не будет продолжаться до тех пор, пока это обещание не будет выполнено.

Таким образом, вы можете приковать count обещание:

agreementQuery.count().then(function() { 
    question.set("agreementCount", count); 
    question.save(null, null); 
}); 

Вы также можете использовать parallel promises, чтобы сделать его более эффективным.

В коде облака нет точек останова, что делает Parse очень сложным в использовании. Только способ регистрирует ваши переменные с помощью console.log

+0

Отлично, спасибо! Я рассмотрю это, а затем приму ваш ответ, увидев, что он работает сегодня вечером. – ArtOfWarfare

+0

Ваш ответ дал мне полезный старт, так что я сделаю +1, но было слишком много кусков, отсутствующих для него, чтобы отметить его как принятое. – ArtOfWarfare

+0

Хорошо, что вы выяснили, что вам нужен массив для параллельных обещаний. без параллельных promoises, вы также можете вернуть 'agreementQuery.count(). then (function() {})' inside 'query.each', поскольку документы говорят, что итерация не будет продолжаться до тех пор, пока это обещание не будет выполнено – knshn

Смежные вопросы