如何判断传入参数是普通JavaScript函数还是Mongoose模型
区分Mongoose模型与普通JavaScript函数的实现方案
Mongoose模型本质虽然是函数,但它自带专属的原型特征和内置属性,通过以下两种方式可以准确区分,不会误判:
- 方案1:原型链校验(最可靠,推荐)
Mongoose通过mongoose.model()生成的模型构造函数,全部继承自mongoose.Model基类,直接校验原型链的准确率最高,适合代码中已经引入mongoose依赖的场景:
const mongoose = require('mongoose'); function someMiddleware(arg1){ if (typeof arg1 !== 'function') { throw new Error('入参仅支持Mongoose模型或普通JavaScript函数'); } // 校验是否为Mongoose模型,兼容直接传入Model基类的极端场景 const isMongooseModel = arg1.prototype instanceof mongoose.Model || arg1 === mongoose.Model; if (isMongooseModel) { // 处理Mongoose模型逻辑 console.log('当前入参是Mongoose模型'); } else { // 处理普通函数逻辑 console.log('当前入参是普通JavaScript函数'); } }
- 方案2:特征属性校验(无mongoose依赖场景用)
如果你的中间件不想硬依赖mongoose包,可以通过Mongoose模型的专属内置属性组合判断,普通自定义函数默认不会携带这些属性:- 存在字符串类型的
modelName属性(存储模型名) - 存在
schema属性(存储绑定的Schema实例) - 存在
find、create、findOne等内置静态查询方法
- 存在字符串类型的
function someMiddleware(arg1){ if (typeof arg1 !== 'function') { throw new Error('入参仅支持Mongoose模型或普通JavaScript函数'); } // 多特征组合判断,避免单属性被手动篡改导致的误判 const isMongooseModel = typeof arg1.modelName === 'string' && !!arg1.schema && typeof arg1.find === 'function' && typeof arg1.create === 'function'; if (isMongooseModel) { // 处理Mongoose模型逻辑 console.log('当前入参是Mongoose模型'); } else { // 处理普通函数逻辑 console.log('当前入参是普通JavaScript函数'); } }
注意:不要使用单个属性做判断,比如仅检查
modelName字段,避免调用方给普通函数手动添加同名属性导致判断错误,多特征组合判断的准确率和原型链校验基本一致。
内容的提问来源于stack exchange,提问作者Islam Y-
相关产品推荐
相关产品推荐

