When sending a request to /customers/41224d776a326fb40f000001
and a document with _id
41224d776a326fb40f000001
does not exist, doc
is null
and I'm returning a 404
:
当发送一个请求到/客户/41224d776a326fb40f000001和一个带有_id 41224d776a326fb40f000001的文档时,doc是空的,我返回的是404:
Controller.prototype.show = function(id, res) {
this.model.findById(id, function(err, doc) {
if (err) {
throw err;
}
if (!doc) {
res.send(404);
}
return res.send(doc);
});
};
However, when _id
does not match what Mongoose expects as "format" (I suppose) for example with GET /customers/foo
a strange error is returned:
但是,当_id与Mongoose所期望的“格式”(我假设)不匹配时,会返回一个奇怪的错误:
CastError: Cast to ObjectId failed for value "foo" at path "_id".
CastError:在path“_id”中,Cast to ObjectId没有值“foo”。
So what's this error?
这个错误是什么?
10 个解决方案
#1
101
Mongoose's findById
method casts the id
parameter to the type of the model's _id
field so that it can properly query for the matching doc. This is an ObjectId but "foo"
is not a valid ObjectId so the cast fails.
Mongoose的findById方法将id参数转换为模型的_id字段的类型,以便它能够正确地查询匹配的文档。这是一个目标,但是“foo”不是一个有效的目标,所以cast失败了。
This doesn't happen with 41224d776a326fb40f000001
because that string is a valid ObjectId.
这不会发生在41224d776a326fb40f000001中,因为该字符串是一个有效的目标。
One way to resolve this is to add a check prior to your findById
call to see if id
is a valid ObjectId or not like so:
解决这一问题的一种方法是在findById调用之前添加一个检查,以查看id是否是一个有效的ObjectId,或者不是这样:
if (id.match(/^[0-9a-fA-F]{24}$/)) {
// Yes, it's a valid ObjectId, proceed with `findById` call.
}
#2
21
Use existing functions for checking ObjectID.
使用现有的功能检查目标。
var mongoose = require('mongoose');
mongoose.Types.ObjectId.isValid('your id here');
#3
8
Are you parsing that string as ObjectId
?
您是否将该字符串解析为ObjectId?
Here in my application, what I do is:
在我的应用中,我所做的是:
ObjectId.fromString( myObjectIdString );
#4
3
You can also use ObjectId.isValid like the following :
你也可以使用ObjectId。其有效性如下:
if (!ObjectId.isValid(userId)) return Error({ status: 422 })
#5
1
if(mongoose.Types.ObjectId.isValid(userId.id)) {
User.findById(userId.id,function (err, doc) {
if(err) {
reject(err);
} else if(doc) {
resolve({success:true,data:doc});
} else {
reject({success:false,data:"no data exist for this id"})
}
});
} else {
reject({success:"false",data:"Please provide correct id"});
}
best is to check validity
最好是检查有效性。
#6
0
I went with an adaptation of the @gustavohenke solution, implementing cast ObjectId in a try-catch wrapped around the original code to leverage the failure of ObjectId casting as a validation method.
我使用了@gustavohenke解决方案的一个修改,实现了在原始代码包装的try-catch中实现cast ObjectId,以利用ObjectId转换失败作为验证方法。
Controller.prototype.show = function(id, res) {
try {
var _id = mongoose.Types.ObjectId.fromString(id);
// the original code stays the same, with _id instead of id:
this.model.findById(_id, function(err, doc) {
if (err) {
throw err;
}
if (!doc) {
res.send(404);
}
return res.send(doc);
});
} catch (err) {
res.json(404, err);
}
};
#7
0
OR you can do this
或者你也可以这么做。
var ObjectId = require('mongoose').Types.ObjectId; var objId = new ObjectId( (param.length < 12) ? "123456789012" : param );
var ObjectId =要求(“猫鼬”).Types.ObjectId;新目标(param)。长度< 12)?“123456789012”:param);
as mentioned here Mongoose's find method with $or condition does not work properly
如上所述,Mongoose的find方法有$or条件不能正常工作。
#8
0
This is an old question but you can also use express-validator package to check request params
这是一个老问题,但是您也可以使用expressvalidator包来检查请求参数。
express-validator version 4 (latest):
express-validator第4版(最新):
validator = require('express-validator/check');
app.get('/show/:id', [
validator.param('id').isMongoId().trim()
], function(req, res) {
// validation result
var errors = validator.validationResult(req);
// check if there are errors
if ( !errors.isEmpty() ) {
return res.send('404');
}
// else
model.findById(req.params.id, function(err, doc) {
return res.send(doc);
});
});
express-validator version 3:
express-validator版本3:
var expressValidator = require('express-validator');
app.use(expressValidator(middlewareOptions));
app.get('/show/:id', function(req, res, next) {
req.checkParams('id').isMongoId();
// validation result
req.getValidationResult().then(function(result) {
// check if there are errors
if ( !result.isEmpty() ) {
return res.send('404');
}
// else
model.findById(req.params.id, function(err, doc) {
return res.send(doc);
});
});
});
#9
0
Always use mongoose.Types.ObjectId('your id')
for conditions in your query it will validate the id field before running your query as a result your app will not crash.
总是使用mongoose.Types。ObjectId('your id')在查询条件下,它将在运行查询之前验证id字段,从而使应用程序不会崩溃。
#10
0
I faced this issue because I was declaring the router as
我面临这个问题,因为我声明路由器为。
router.put('/:id', async (req, res) => {
// code ....
}
and was updating the data with url i.e.
并使用url更新数据。
http://localhost:3000/id=5af584ebb62aae2fa8e406a2
After spending a long time I correct myself by removing id=
as
在花费了很长时间之后,我通过删除id=来纠正自己。
the right way was:
正确的方法是:
http://localhost:3000/5af584ebb62aae2fa8e406a2
Now I am able to use findById()
as
现在我可以使用findById()了。
let myModel = await Model.findById(req.params.id);
#1
101
Mongoose's findById
method casts the id
parameter to the type of the model's _id
field so that it can properly query for the matching doc. This is an ObjectId but "foo"
is not a valid ObjectId so the cast fails.
Mongoose的findById方法将id参数转换为模型的_id字段的类型,以便它能够正确地查询匹配的文档。这是一个目标,但是“foo”不是一个有效的目标,所以cast失败了。
This doesn't happen with 41224d776a326fb40f000001
because that string is a valid ObjectId.
这不会发生在41224d776a326fb40f000001中,因为该字符串是一个有效的目标。
One way to resolve this is to add a check prior to your findById
call to see if id
is a valid ObjectId or not like so:
解决这一问题的一种方法是在findById调用之前添加一个检查,以查看id是否是一个有效的ObjectId,或者不是这样:
if (id.match(/^[0-9a-fA-F]{24}$/)) {
// Yes, it's a valid ObjectId, proceed with `findById` call.
}
#2
21
Use existing functions for checking ObjectID.
使用现有的功能检查目标。
var mongoose = require('mongoose');
mongoose.Types.ObjectId.isValid('your id here');
#3
8
Are you parsing that string as ObjectId
?
您是否将该字符串解析为ObjectId?
Here in my application, what I do is:
在我的应用中,我所做的是:
ObjectId.fromString( myObjectIdString );
#4
3
You can also use ObjectId.isValid like the following :
你也可以使用ObjectId。其有效性如下:
if (!ObjectId.isValid(userId)) return Error({ status: 422 })
#5
1
if(mongoose.Types.ObjectId.isValid(userId.id)) {
User.findById(userId.id,function (err, doc) {
if(err) {
reject(err);
} else if(doc) {
resolve({success:true,data:doc});
} else {
reject({success:false,data:"no data exist for this id"})
}
});
} else {
reject({success:"false",data:"Please provide correct id"});
}
best is to check validity
最好是检查有效性。
#6
0
I went with an adaptation of the @gustavohenke solution, implementing cast ObjectId in a try-catch wrapped around the original code to leverage the failure of ObjectId casting as a validation method.
我使用了@gustavohenke解决方案的一个修改,实现了在原始代码包装的try-catch中实现cast ObjectId,以利用ObjectId转换失败作为验证方法。
Controller.prototype.show = function(id, res) {
try {
var _id = mongoose.Types.ObjectId.fromString(id);
// the original code stays the same, with _id instead of id:
this.model.findById(_id, function(err, doc) {
if (err) {
throw err;
}
if (!doc) {
res.send(404);
}
return res.send(doc);
});
} catch (err) {
res.json(404, err);
}
};
#7
0
OR you can do this
或者你也可以这么做。
var ObjectId = require('mongoose').Types.ObjectId; var objId = new ObjectId( (param.length < 12) ? "123456789012" : param );
var ObjectId =要求(“猫鼬”).Types.ObjectId;新目标(param)。长度< 12)?“123456789012”:param);
as mentioned here Mongoose's find method with $or condition does not work properly
如上所述,Mongoose的find方法有$or条件不能正常工作。
#8
0
This is an old question but you can also use express-validator package to check request params
这是一个老问题,但是您也可以使用expressvalidator包来检查请求参数。
express-validator version 4 (latest):
express-validator第4版(最新):
validator = require('express-validator/check');
app.get('/show/:id', [
validator.param('id').isMongoId().trim()
], function(req, res) {
// validation result
var errors = validator.validationResult(req);
// check if there are errors
if ( !errors.isEmpty() ) {
return res.send('404');
}
// else
model.findById(req.params.id, function(err, doc) {
return res.send(doc);
});
});
express-validator version 3:
express-validator版本3:
var expressValidator = require('express-validator');
app.use(expressValidator(middlewareOptions));
app.get('/show/:id', function(req, res, next) {
req.checkParams('id').isMongoId();
// validation result
req.getValidationResult().then(function(result) {
// check if there are errors
if ( !result.isEmpty() ) {
return res.send('404');
}
// else
model.findById(req.params.id, function(err, doc) {
return res.send(doc);
});
});
});
#9
0
Always use mongoose.Types.ObjectId('your id')
for conditions in your query it will validate the id field before running your query as a result your app will not crash.
总是使用mongoose.Types。ObjectId('your id')在查询条件下,它将在运行查询之前验证id字段,从而使应用程序不会崩溃。
#10
0
I faced this issue because I was declaring the router as
我面临这个问题,因为我声明路由器为。
router.put('/:id', async (req, res) => {
// code ....
}
and was updating the data with url i.e.
并使用url更新数据。
http://localhost:3000/id=5af584ebb62aae2fa8e406a2
After spending a long time I correct myself by removing id=
as
在花费了很长时间之后,我通过删除id=来纠正自己。
the right way was:
正确的方法是:
http://localhost:3000/5af584ebb62aae2fa8e406a2
Now I am able to use findById()
as
现在我可以使用findById()了。
let myModel = await Model.findById(req.params.id);