我在back4app上托管了一个Parse Server应用程序,并且正在运行后台作业,该作业每分钟运行一次并查询Letters
类,其中deliveryDate
列小于或等于当前日期,这是我的main.js文件:
// DELIVER A LETTER
Parse.Cloud.job("deliverLetter", function (request, status) {
var now = new Date();
// var nowTime = date.getTime();
var Letters = Parse.Object.extend("Letters");
var query = new Parse.Query(Letters);
query.lessThanOrEqualTo("deliveryDate", now);
query.find().then (function (objects) {
objects.forEach(function (obj) {
obj.set("isDelivered", true);
Parse.Cloud.useMasterKey();
obj.save(null, { useMasterKey: true } ).then(function(obj) {
response.success(obj);
}, function(error) {
response.error(error)
});
});
});
因此,例如,我在
deliveryDate
设置为昨天的Letters类中保存了一行,以便我测试此Cloud Code函数。还有另一列称为isDelivered
,并将其设置为False。因此,我上面的函数应将isDelivered
设置为True并更新我的Letters
对象。但这是行不通的,所以我不知道自己在做什么错。
编辑
多亏了
danh
,我已修复了代码,如下所示:var Letters = Parse.Object.extend("Letters");
var query = new Parse.Query(Letters);
query.lessThanOrEqualTo("deliveryDate", now);
query.equalTo("isDelivered", false);
query.find().then (function (objects) {
let savePromises = objects.map(function (obj) {
obj.set("isDelivered", true);
return obj.save(null, { useMasterKey: true } );
});
Promise.all(savePromises).then(function(obj) {
response.success(obj);
}, function(error) {
response.error(error)
});
});
我需要从main.js文件中调用另一个函数,该函数发送推送通知并需要一些参数。我通常从我的应用程序中调用它,如何从上述函数中调用它?
Parse.Cloud.define("pushiOS", function(request, response) {
var user = request.user;
var params = request.params;
var userObjectID = params.userObjectID
var data = params.data
var recipientUser = new Parse.User();
recipientUser.id = userObjectID;
var pushQuery = new Parse.Query(Parse.Installation);
pushQuery.equalTo("userID", userObjectID);
Parse.Push.send({
where: pushQuery,
data: data
}, { success: function() {
console.log("#### PUSH SENT!");
}, error: function(error) {
console.log("#### PUSH ERROR: " + error.message);
}, useMasterKey: true});
response.success('success');
});
也许进入Promise.all()?
Promise.all(savePromises).then(function(obj) {
response.success(obj);
Parse.Cloud.define("pushiOS"...
}, function(error) {
response.error(error)
});
最佳答案
调用save()
时正在进行的或尚未启动的任何response.success()
将被终止(或无法获得启动的机会)。要修复,请收集所有保存的承诺,然后与Promise.all()
一起运行它们,而query.lessThanOrEqualTo("deliveryDate", now);
仅在传递给它的所有承诺都解决后才能解析。
query.find().then (function (objects) {
// Parse.Cloud.useMasterKey(); don't need this
let savePromises = objects.map(function (obj) {
obj.set("isDelivered", true);
return obj.save(null, { useMasterKey: true } );
});
Promise.all(savePromises).then(function(obj) {
response.success(obj);
}, function(error) {
response.error(error)
});
});
另外,请注意,顺便说一句,将在此之前获得所有带有deliveryDates的对象,包括您先前处理过的对象。随着时间的推移,该结果将单调地变长,最终在两次运行之间超过1分钟,或者消耗其他系统资源。
也许你真的想要...
query.lessThanOrEqualTo("deliveryDate", now);
query.equalTo("isDelivered", false);
编辑
第二个问题可以通过将像这样的promise-returning push函数分解为因子来处理。
function pushDataToUser(userID, data)
var recipientUser = new Parse.User();
recipientUser.id = userID;
let pushQuery = new Parse.Query(Parse.Installation);
pushQuery.equalTo("userID", userID);
return Parse.Push.send({ where:pushQuery, data:data });
}
可以从这样的云代码中调用...
Parse.Cloud.define("pushiOS", function(request, response) {
let params = request.params;
pushDataToUser(params.userObjectID, params.data).then(function() {
console.log("#### PUSH SENT!");
response.success('success');
}, function(error) {
console.log("#### PUSH ERROR! " + JSON.stringify(error));
response.error(error);
});
}
...并且可以将新的承诺返回功能添加到任何其他这样的承诺链中...
// function doSomething() returns a promise (like from a find() or a save()
return doSomething().then(function() {
// initialize someId and someData
return pushDataToUser(someId, someData)
});