环回 - "next()" 未在 "beforeRemote" 的正确时间触发?
loopback - "next()" not firing at the correct time in "beforeRemote"?
我正在尝试在 find 方法返回结果之前从远程源更新数据库。我正在尝试对 "find" 操作使用 "beforeRemote" 方法。它正在更新数据库,但不会等到数据库更新完成才返回数据。我可以这么说,因为我第一次针对空数据库调用 "find" 端点时,结果是空的,但是在调用之后检查数据库时,它里面有数据。
这是我的模型class(删除了敏感内容)。
'use strict';
var Cronofy = require('cronofy');
var _ = require('lodash');
module.exports = function (Event) {
// remote method before hook
Event.beforeRemote('find', function (ctx, unused, next) {
var client = new Cronofy({
access_token: 'secret-token',
});
var options = {
from: "2018-10-15",
to: "2018-11-15",
tzid: 'Etc/UTC'
};
client.readEvents(options)
.then(function (response) {
var returnedEvents = response.events;
var events = _.filter(returnedEvents, function(o){
return !_.isEmpty(o.summary) && !_.isEmpty(o.event_uid) && !_.isEmpty(o.start) && !_.isEmpty(o.end);
});
events.forEach(element => {
Event.upsertWithWhere({
sourceType: "external-source-a",
sourceID: element.event_uid
}, {
sourceType: "external-source-a",
sourceID: element.event_uid,
summary: element.summary,
description: element.description,
start: element.start,
end: element.end,
recurring: element.recurring
},
function (err, model) {
if (err) {
console.log(err);
}
//console.log(model);
}
);
});
next();
}).catch(console.log);
});
};
我是环回的新手,所以我确定这是一个简单的错误。我做错了什么?
使用Promise.allPromise.all
在更新的情况下,您不应将 forEach 与异步操作一起使用,因为 forEach 不会等到更新完成后再调用 next。
相反,例如使用 map 来循环事件和 return 更新操作的承诺,这样您就可以创建承诺数组并使用 Promise.all。
在then的Promise.all调用next方法。
module.exports = function (Event) {
// remote method before hook
Event.beforeRemote('find', function (ctx, unused, next) {
var client = new Cronofy({
access_token: 'secret-token',
});
var options = {
from: "2018-10-15",
to: "2018-11-15",
tzid: 'Etc/UTC'
};
client.readEvents(options)
.then(function (response) {
var returnedEvents = response.events;
var events = _.filter(returnedEvents, function(o){
return !_.isEmpty(o.summary) && !_.isEmpty(o.event_uid) && !_.isEmpty(o.start) && !_.isEmpty(o.end);
});
const updatepromises = events.map((element) => {
return Event.upsertWithWhere({
sourceType: "external-source-a",
sourceID: element.event_uid
}, {
sourceType: "external-source-a",
sourceID: element.event_uid,
summary: element.summary,
description: element.description,
start: element.start,
end: element.end,
recurring: element.recurring
});
});
return Promise.all(updatepromises);
})
.then((result) => next())
.catch(console.log);
});
};
或者您可以使用 async/await async/await,它更具可读性,您不必调用 next loopback 会为您处理。
module.exports = function (Event) {
// remote method before hook
Event.beforeRemote('find', async function (ctx, unused) {
var client = new Cronofy({
access_token: 'secret-token',
});
var options = {
from: "2018-10-15",
to: "2018-11-15",
tzid: 'Etc/UTC'
};
var response = await client.readEvents(options);
var returnedEvents = response.events;
var events = _.filter(returnedEvents, function (o) {
return !_.isEmpty(o.summary) && !_.isEmpty(o.event_uid) && !_.isEmpty(o.start) && !_.isEmpty(o.end);
});
const updatepromises = events.map((element) => {
return Event.upsertWithWhere({
sourceType: "external-source-a",
sourceID: element.event_uid
}, {
sourceType: "external-source-a",
sourceID: element.event_uid,
summary: element.summary,
description: element.description,
start: element.start,
end: element.end,
recurring: element.recurring
});
});
await Promise.all(updatepromises);
});
};
我正在尝试在 find 方法返回结果之前从远程源更新数据库。我正在尝试对 "find" 操作使用 "beforeRemote" 方法。它正在更新数据库,但不会等到数据库更新完成才返回数据。我可以这么说,因为我第一次针对空数据库调用 "find" 端点时,结果是空的,但是在调用之后检查数据库时,它里面有数据。
这是我的模型class(删除了敏感内容)。
'use strict';
var Cronofy = require('cronofy');
var _ = require('lodash');
module.exports = function (Event) {
// remote method before hook
Event.beforeRemote('find', function (ctx, unused, next) {
var client = new Cronofy({
access_token: 'secret-token',
});
var options = {
from: "2018-10-15",
to: "2018-11-15",
tzid: 'Etc/UTC'
};
client.readEvents(options)
.then(function (response) {
var returnedEvents = response.events;
var events = _.filter(returnedEvents, function(o){
return !_.isEmpty(o.summary) && !_.isEmpty(o.event_uid) && !_.isEmpty(o.start) && !_.isEmpty(o.end);
});
events.forEach(element => {
Event.upsertWithWhere({
sourceType: "external-source-a",
sourceID: element.event_uid
}, {
sourceType: "external-source-a",
sourceID: element.event_uid,
summary: element.summary,
description: element.description,
start: element.start,
end: element.end,
recurring: element.recurring
},
function (err, model) {
if (err) {
console.log(err);
}
//console.log(model);
}
);
});
next();
}).catch(console.log);
});
};
我是环回的新手,所以我确定这是一个简单的错误。我做错了什么?
使用Promise.allPromise.all
在更新的情况下,您不应将 forEach 与异步操作一起使用,因为 forEach 不会等到更新完成后再调用 next。 相反,例如使用 map 来循环事件和 return 更新操作的承诺,这样您就可以创建承诺数组并使用 Promise.all。 在then的Promise.all调用next方法。
module.exports = function (Event) {
// remote method before hook
Event.beforeRemote('find', function (ctx, unused, next) {
var client = new Cronofy({
access_token: 'secret-token',
});
var options = {
from: "2018-10-15",
to: "2018-11-15",
tzid: 'Etc/UTC'
};
client.readEvents(options)
.then(function (response) {
var returnedEvents = response.events;
var events = _.filter(returnedEvents, function(o){
return !_.isEmpty(o.summary) && !_.isEmpty(o.event_uid) && !_.isEmpty(o.start) && !_.isEmpty(o.end);
});
const updatepromises = events.map((element) => {
return Event.upsertWithWhere({
sourceType: "external-source-a",
sourceID: element.event_uid
}, {
sourceType: "external-source-a",
sourceID: element.event_uid,
summary: element.summary,
description: element.description,
start: element.start,
end: element.end,
recurring: element.recurring
});
});
return Promise.all(updatepromises);
})
.then((result) => next())
.catch(console.log);
});
};
或者您可以使用 async/await async/await,它更具可读性,您不必调用 next loopback 会为您处理。
module.exports = function (Event) {
// remote method before hook
Event.beforeRemote('find', async function (ctx, unused) {
var client = new Cronofy({
access_token: 'secret-token',
});
var options = {
from: "2018-10-15",
to: "2018-11-15",
tzid: 'Etc/UTC'
};
var response = await client.readEvents(options);
var returnedEvents = response.events;
var events = _.filter(returnedEvents, function (o) {
return !_.isEmpty(o.summary) && !_.isEmpty(o.event_uid) && !_.isEmpty(o.start) && !_.isEmpty(o.end);
});
const updatepromises = events.map((element) => {
return Event.upsertWithWhere({
sourceType: "external-source-a",
sourceID: element.event_uid
}, {
sourceType: "external-source-a",
sourceID: element.event_uid,
summary: element.summary,
description: element.description,
start: element.start,
end: element.end,
recurring: element.recurring
});
});
await Promise.all(updatepromises);
});
};