nodejs使用mongodb将string类型id转换为ObjectId失败问题

一、问题描述

通过NodeJs操作MongoDb数据库,在删除操作中使用主键id做为条件:

nodejs使用mongodb将string类型id转换为ObjectId失败问题_第1张图片
删除语句

有接触过mongodb的都知道这里的id是要传入ObjectId对象的,不能直接传字符串类型。

但是我在此处将字符串id转换成ObjectId时,却报如下错误:

UnhandledPromiseRejectionWarning: Error: Argument passed in must be

a single String of 12 bytes or a string of 24 hex characters

二、问题分析

查询官网,可以通过以下几种方式将String转换为ObjectId:

1、使用ObjectId(id)

2、使用new ObjectId(id) 

3、使用静态方法ObjectId.createFromHexString(id)

然而使用以上三种方法依然出现上述错误。

但是直接使用id变量的值"5c640413d63e990b8478f6fd"来转换时是正常的:

deleteOne({_id:ObjectId("5c640413d63e990b8478f6fd")}) 

难道id变量和常量有什么不同吗?打印id变量类型,确实为string,显示的字符串内容也一样。

查看错误提示,代码调用堆栈如下:

错误堆栈

找到objectid.js对应源码:

nodejs使用mongodb将string类型id转换为ObjectId失败问题_第2张图片
出错日志对应源码

可以看到是长度不对。

打印id变量长度,以及各个字符值:

打印id变量字符
nodejs使用mongodb将string类型id转换为ObjectId失败问题_第3张图片
id变量字符

id变量字符串开头和结尾各多了一对单引号,这是怎么来的呢?

于是理一下数据流程,从数据源头开始查找。最早这个id是从数据库中查找的,经调试此时还是object类型,且转成string类型后长度是24,说明这时候是正常的。之后在界面中使用模板时传递参数过程出现了数据转换:

1、界面 home.art:

经测试此时_id转成string长度还是24

2、接口映射 app.js:

app.get('/delete_interface/:id',delete_interface)

经测试此时传入delete_interface的参数id字符串长度为26,数据转换过程中发生了变化!

三、问题解决

模板代码中在传递参数前将id变量从object类型转换成string类型

测试传入delete_interface的参数id字符串长度为24,数据库删除操作没有再报错,问题解决。

需要注意要在传参前进行类型转换,在delete_interface拿到参数后再进行转换是没用的。

四、总结

分析问题时,

1、不要被表面现象迷惑,比如查看id字符串内容看不出问题,但是查看长度及字符ascii码则明显能看出来

2、查看错误日志,分析错误堆栈,查看源码

3、分析代码和数据经过流程

你可能感兴趣的:(nodejs使用mongodb将string类型id转换为ObjectId失败问题)