Asynchronous Sails findOrCreate returns“;“记录已存在”;如果异步运行
使用sails.js,我有一个使用.findOrCreate(…)的服务 如果使用相同的数据同时调用此服务两次,它将返回“记录已存在”错误 这是一个已知的问题吗?有什么克服它的建议吗 更新: 我正在使用sails mysql。Asynchronous Sails findOrCreate returns“;“记录已存在”;如果异步运行,asynchronous,sails.js,waterline,Asynchronous,Sails.js,Waterline,使用sails.js,我有一个使用.findOrCreate(…)的服务 如果使用相同的数据同时调用此服务两次,它将返回“记录已存在”错误 这是一个已知的问题吗?有什么克服它的建议吗 更新: 我正在使用sails mysql。 查询字段被设置为唯一(这就是为什么我得到这个错误,否则会创建重复项),并且也被设置为索引(如中所建议) 更新2: Show.js: tmdbId: { type: 'integer', unique: true, index: true }, name: {
查询字段被设置为唯一(这就是为什么我得到这个错误,否则会创建重复项),并且也被设置为索引(如中所建议) 更新2: Show.js:
tmdbId: {
type: 'integer',
unique: true,
index: true
},
name: {
type: 'string',
required: true
},
slug: {
type: 'string',
required: true,
unique: true
},
seasons: {
collection: 'season',
via: 'show'
},
episodes: {
collection: 'episode',
via: 'show'
}
服务:
Show.findOrCreate({
tmdbId: req.tmdbId
}, {
tmdbId: req.tmdbId,
name: req.showName,
slug: Services.slug(req.showName)
}).exec(function (err, show) {
if (err)
return sails.log.error(err);
Season.findOrCreate({
show: show.id,
number: req.season
}).exec(function (err, season) {
if (err)
return sails.log.error(err);
Episode.findOrCreate({
show: show.id,
season: season.id,
number: req.episode,
airDate: req.airDate
}).exec(function (err, episode) {
if (err)
return sails.log.error(err);
return res;
})
})
})
您的
季
和集
findOrCreate
不符合Sails惯例。尝试:
Show
.findOrCreate({
tmdbId: req.tmdbId
}, {
tmdbId: req.tmdbId,
name: req.showName,
slug: Services.slug(req.showName)
})
.exec(function (err, show) {
if (err) return sails.log.error(err);
Season
.findOrCreate({
show: show.id
}, {
show: show.id,
number: req.season
})
.exec(function (err, season) {
if (err) return sails.log.error(err);
Episode
.findOrCreate({
show: show.id
}, {
show: show.id,
season: season.id,
number: req.episode,
airDate: req.airDate
})
.exec(function (err, episode) {
if (err) return sails.log.error(err);
return res;
})
})
})
我在postgres适配器上也遇到过同样的问题,我认为原因是比赛条件。这似乎是一个已知的问题:
findOrCreate
看起来不是原子的,因此我认为第一个调用执行一个find
查询,该查询在执行创建操作之前不返回任何结果。如果第二个调用在第一个调用的create
完成之前执行其find
,它也会返回一个空结果,从而触发另一个create
如果create
数据包含唯一值,则会出现问题。由于执行了两个create
操作,将添加两次相同的数据,因此第二个操作将失败,因为数据库中已存在唯一值。如果没有标记为唯一的值
,则结果是重复的
解决此问题的一种方法是捕获错误,并在catch块中执行
find
查询,因为我们知道条目现在存在,然后是您打算首先执行的任何操作。但不幸的是,在您的示例中,这种方法确实变得非常丑陋,因为嵌套的findOrCreate
调用需要各自的catch块。您能写下您的查询吗?比如Model.findOrCreate({id:1},{name:'some name'})