我目前正在构建一个Web应用程序,我偶然发现了过去12小时内无法解决的问题。
我正在研究一种基本的get方法,我正在尝试检索员工工作的某些工作岗位(即收银员,职员)(客户端工作正常)。
WorkPosition的猫鼬模型是这样的(models / work-position.js):
var mongoose = require('mongoose');
var User = require('./user');
var Schema = mongoose.Schema;
var schema = new Schema ({
workplace : {type: String, required: true},
type : {type: String, required: true},
status : {type: String, required: true},
color : {type: String, required: true},
employees: [{type: Schema.Types.ObjectId, ref:'User'}]
});
module.exports = mongoose.model('WorkPosition', schema);
我的get方法(routes / work-position.js):
var express = require('express');
var router = express.Router();
var jwt = require('jsonwebtoken');
var User = require('../models/user');
var mongoose = require('mongoose');
var WorkPosition = require('../models/work-position');
router.get('/:userId', function(req, res, next) {
const userId = req.params.userId;
WorkPosition.find({employees: {$elemMatch : {$eq: userId}}})
.exec(function(err, workPositions) {
if(err) {
return res.status(500).json({
title: 'an error has occurred',
error: err
});
}
console.log(userId);
console.log(workPositions);
res.status(200).json({
message: 'Success',
obj: workPositions
});
});
});
当我尝试使用$ elemMatch方法时出现问题。当WorkPosition.find行更改为
时,上面的代码WorkPosition.find()
没有任何条件(
{employees: {$elemMatch : {$eq: userId}}}
)在里面,我成功地能够检索出我想要的WorkPosition文档。
但是,我想只检索'员工' WorkPosition中的字段匹配' userId'我收到了req.params。因此,我搜索了mongodb / mongoose API(http://mongoosejs.com/docs/api.html#query_Query-elemMatch)
我找到了$ elemMatch方法。
在mongodb shell中,当我做
时db.workpositions.find({"employees": { $elemMatch : {$eq: "596823efbac11d1978ba2ee9"}}})
其中" 5968 ...."是userId,我成功地能够查询WorkPosition文档。
通过这个命令,我能够验证我的逻辑是否正确,并使用mongodb native shell命令获取我想要的文档。
但是,当我尝试将相同的逻辑转换为Mongoose API时,即:
WorkPosition.find().elemMatch('employees', {$eq : userId})
我得到一个空数组,并添加行
mongoose.set('debug', function (coll, method, query, doc) {
console.log(coll + " " + method + " " + JSON.stringify(query) + " " + JSON.stringify(doc));
});
在/app.js中,我能够看到mongoose查询转换为本机mongodb命令是什么:
workpositions find {"employees":{"$elemMatch":{"$eq":"596823efbac11d1978ba2ee9"}}} {"fields":{}}
。集合(工作位置),方法(查找),要搜索的数组(员工)和所有内容都正确地转换为本机mongodb命令除了
"$eq"
。成功运行的shell命令与我的代码中的mongoose命令之间的唯一区别是' $ eq'附近的引号。
壳:
db.workpositions.find({"employees": { $elemMatch : {$eq: "596823efbac11d1978ba2ee9"}}})
猫鼬:
db.workpositions.find({"employees": { $elemMatch : {"$eq": "596823efbac11d1978ba2ee9"}}})
我似乎无法找到摆脱这些额外引号的方法(我认为这是引起问题的原因)。我尝试使用带有mongoose的本机命令,如:
mongoose.connection.db.workpositions.find(.....)
但这也会导致错误。
通过猫鼬使用elemMatch的正确方法是什么?任何人都可以启发我如何使用它?我尝试了各种我能想到的方式,似乎无法解决这个问题。
我正在考虑更改WorkPosition.employees字段,以便它保存实际用户(不仅仅是userIds),并且我可以解析与Mongoose elemMatch API完全匹配的其他信息。但是,我相信这会浪费大量的数据库空间,因为每个WorkPosition都必须携带一组用户。
要在Users和WorkPosition之间建立正确的关系,elemMatch是我项目中的一项要求。我非常感谢任何帮助!
答案 0 :(得分:0)
在比较mongodb ObjectId时,请在$ eq数组运算符周围使用 mongoose.Types.ObjectId ,然后您可以使用$ elemMatch运算符检索符合条件的第一个文档。
$ elemMatch:{$ eq:mongoose.Types.ObjectId(userId)}