我正在构建一个sails.js api与MongoDb作为我的数据库。
这些是我的模型(为了这个问题而简化):
models/Passport.js
简化:
identifier: {
type: 'string'
},
owner: {
model: 'User',
required: true
},
models/User.js
简化:
username: {
type: 'string',
unique: true
},
passports: {
collection: 'Passport',
via: 'owner'
}
问题
在sails.js服务login
函数中,我首先尝试通过User
集合的用户名获取用户。
sails.models.user.findOne({username: 'demo'}).exec(function onExec(error, user) {
user; //contains user info
}
然后,当获取用户时(这是成功的),我抓取他的用户。id并尝试从passport collection中取出他的护照。
sails.models.passport.findOne({owner:user.id}).exec(function onExec(error, passp) {
if(passp==undefined) //puppies dying in this line!!!!
throw new Error('Can't find this passport');
}
}
返回的passp
对象未定义。什么…为什么?
附加信息:
在我的mongo shell中运行> db.passport.find({owner:"theCorrectUserId"})
确实返回正确的护照,因此它不是一个不正确的id的问题,而且,运行:
sails.models.passport.find().exec(function onExec(error, passports) {
passports; //does contain all my passports
}
确实包含我所有的护照。因此,这不是一个编程错误!
啊哈时刻:
经过几个小时的绞尽脑汁,我发现删除了的关联,从而使我的模型如下:
models/Passport.js
简体:
identifier: {
type: 'string'
},
owner: {
type: 'string'
required: true
}
models/User.js
简体:
username: {
type: 'string',
unique: true
}
解决了这个问题,并使我的passp
对象获取正确的数据。
我使用水线协会错误吗?但是,当关联存在时,为什么它在mongo shell中起作用呢?
如果我在我的服务中使用2个不同的查询,我甚至需要关联吗?性能怎么样?
让我们使用第一个模型架构。
你应该这样做的水线:
sails.models.user
.findOne({ username: username })
// The populate method allows you to get associated data
.populate('passports')
.exec(function (err, user) {
// Handle errors
if(err) return next('An unknown error has occured');
if(!user) return next('Can't find this user');
if(!user.passports || !user.passports.length)
return next('This user has no passports');
// The User has at least one passport
...
return next(null, user);
}
next
方法将您带回到控制器。以下是你应该如何使用你的服务:
sails.services.myService
.login(username, password, function (err, user) {
...
});
如您所见,只剩下一个查询:-)。
这里是与Sails ORM相关的文档
而不是:
sails.models.passport.findOne({owner:user.id})
试题:
sails.models.passport.findOne({owner:user})