Sequelize导入nanoid报ES Module不支持require()错误
问题根因
报错由模块系统不匹配直接导致:
- 你的
tsconfig.json中module项配置为commonjs,TypeScript编译时会把所有import语句转为CommonJS规范的require()调用 - 当前安装的nanoid v4及以上版本为纯ES Module包,不支持CommonJS的
require()直接导入 - 之前在
package.json添加"type":"module"未生效,是因为TS编译输出的代码仍然是CommonJS格式,模块规范没有对齐。
解决方案
按改造成本从低到高可任选其一:
方案1:降级nanoid到v3版本(推荐,零业务代码改动)
nanoid v3是官方长期维护的稳定版本,原生支持CommonJS,API和v4+完全兼容,直接执行对应包管理器的安装命令即可:
npm install nanoid@3.x # yarn 用户执行 # yarn add nanoid@3.x # pnpm 用户执行 # pnpm add nanoid@3.x
安装完成后原有静态导入写法import { nanoid } from 'nanoid'可正常运行,无需修改其他逻辑。
方案2:保留新版nanoid,改用动态导入适配
如果需要使用nanoid v4+的新特性,可将静态导入改为CommonJS环境支持的动态import()写法,Sequelize原生支持异步钩子:
- 删除文件顶部的
import { nanoid } from 'nanoid'静态导入语句 - 修改
beforeCreate钩子为异步函数,在内部动态加载nanoid,同时修正代码中的字段笔误:
// 其余模型配置保持不变,仅修改hooks中的beforeCreate逻辑 hooks: { beforeCreate: async (attributes: any, options: any) => { const { nanoid } = await import('nanoid') const id = !!attributes.cId options.rqType = options.updateOnDuplicate ? id ? 'BULKUPDATE' : 'BULKCREATE' : 'CREATE' // 修正笔误:原代码赋值给不存在的pId字段,模型主键为cId attributes.cId = attributes.cId || nanoid(32) return options }, // afterUpdate、afterCreate钩子保持原有逻辑即可 }
方案3:全项目切换为ES Module规范(改动量大,非必要不选)
如果要全项目统一使用ESM规范,需修改以下配置:
- 保留
package.json中的"type":"module"配置 - 调整
tsconfig.json的模块相关配置:{ "compilerOptions": { "module": "NodeNext", "moduleResolution": "NodeNext" // 其余配置保持不变 } } - 补全所有相对导入的文件后缀(例如
import utils from './utils'需改为import utils from './utils.js'),调整项目内所有CommonJS格式的配置文件为ESM格式,整体改造成本较高。
额外问题提示
你当前的模型代码还有两处隐藏问题:
db.define传入的第一个表名参数为'comments',和分类模型的语义不符,建议确认是否为笔误beforeCreate钩子中给不存在的pId字段赋值会被Sequelize忽略,最终会因主键cId为空触发数据库非空约束错误,必须修正。
内容的提问来源于stack exchange,提问作者anderson sanchez
相关产品推荐
相关产品推荐

