You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node.js v20.6.0安装Shadcn组件时Babel报错原因咨询

Node.js v20.6.0安装Shadcn组件时Babel报错的原因及机制解析

问题重现

在Next.js项目中使用Shadcn组件,Node.js版本为v20.6.0时,安装组件触发如下Babel报错:

C:\Users\lesli\AppData\Local\npm-cache\_npx\d66c5096c7023bfb\node_modules\@babel\core\lib\index.js:7
Object.defineProperty(exports, "File", {
       ^

TypeError: Cannot redefine property: File
    at Function.defineProperty (<anonymous>)
    at Object.<anonymous> (C:\Users\lesli\AppData\Local\npm-cache\_npx\d66c5096c7023bfb\node_modules\@babel\core\lib\index.js:7:8)
    at Module._compile (node:internal/modules/cjs/loader:1241:14)
    at Module._extensions..js (node:internal/modules/cjs/loader:1295:10)
    at Module.load (node:internal/modules/cjs/loader:1091:32)
    at Module._load (node:internal/modules/cjs/loader:938:12)
    at Module.require (node:internal/modules/cjs/loader:1115:19)
    at require (node:internal/modules/helpers:130:18)
    at Object.<anonymous> (C:\Users\lesli\AppData\Local\npm-cache\_npx\d66c5096c7023bfb\node_modules\@babel\core\lib\config\helpers\config-api.js:16:14)
    at Module._compile (node:internal/modules/cjs/loader:1241:14)

已通过升级Node.js至最新版本或降级至v20.5.1解决问题,现需了解报错原因及Babel与Object.defineProperty的运行机制。

报错具体原因

  • Node.js v20.6.0引入了CommonJS模块加载的兼容性bug:处理部分npm包的模块导出时,会错误地将exports对象上的属性标记为不可配置(configurable: false)。
  • Babel的@babel/core模块初始化时,会通过Object.defineProperty(exports, "File", ...)尝试给exports添加属性,但此时该属性已被Node.js加载器错误设置为不可配置,导致调用失败——因为若目标属性已存在且不可配置,Object.defineProperty无法重新定义它,进而抛出Cannot redefine property错误。
  • 该bug在Node.js v20.5.1及更早版本不存在,后续补丁版本也修复了此问题,因此升级或降级Node.js均可解决报错。

Babel与Object.defineProperty的运行机制

1. Object.defineProperty的核心行为

Object.defineProperty(obj, prop, descriptor)是JS中用于精确控制对象属性的API,核心规则如下:

  • 若目标属性不存在,会按照descriptor的配置创建新属性,默认configurable、enumerable、writable均为false。
  • 若目标属性已存在:
    • 若原属性的configurable为false,则无法修改属性的configurable、enumerable,也无法在数据属性和访问器属性之间转换,强行操作会抛出错误。
    • 若原属性writable: false,则无法修改其值,除非同时将writable设为true。

2. Babel中对该API的使用

Babel的模块(如@babel/core)采用CommonJS规范导出成员,为了精确控制导出属性的行为(比如禁止后续修改、控制枚举性),会使用Object.defineProperty替代直接赋值(exports.File = ...):

  • 直接赋值的属性默认是可配置、可写、可枚举的,而Object.defineProperty能更严格地控制这些特性,避免导出的API被意外修改。
  • 在正常Node.js版本中,exports对象的初始属性均为可配置状态,Babel的调用不会有问题;但Node.js v20.6.0的bug打破了这个前提,最终触发报错。

内容的提问来源于stack exchange,提问作者Leslie Wubbel

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.13 15:06:05