构建时导入jest-lite出现Window is not defined问题及解决尝试
解决Next.js中jest-lite生产构建报错的方案
问题原因
Next.js生产构建时会执行服务端渲染(SSR)或静态生成(SSG),此时运行环境是Node.js,不存在window对象。而jest-lite的核心逻辑依赖window,直接在组件中导入会触发服务端渲染阶段报错。另外如果jest-lite安装在devDependencies中,或者导入路径不正确,会出现Can't resolve 'jest-lite'的错误。
方案一:用Next.js动态导入禁用SSR
利用Next.js的dynamic函数,强制jest-lite仅在客户端加载,彻底避开服务端环境:
import dynamic from 'next/dynamic'; // 动态导入并解构需要的测试方法 const JestUtils = dynamic( () => import('jest-lite').then(module => ({ describe: module.describe, it: module.it, expect: module.expect, run: module.run })), { ssr: false, // 禁止服务端渲染该模块 loading: () => <p>加载测试工具...</p> } ); export default function TestPage() { return ( <div> <JestUtils.Consumer> {utils => { if (!utils) return <p>工具加载中...</p>; // 在这里编写测试逻辑 utils.describe('示例测试', () => { utils.it('1+1等于2', () => { utils.expect(1 + 1).toBe(2); }); }); utils.run(); return <p>测试已执行完成</p>; }} </JestUtils.Consumer> </div> ); }
方案二:在useEffect中动态导入(更推荐)
useEffect钩子仅在客户端执行,完全不会涉及服务端渲染,是更稳妥的方式:
import { useEffect, useState } from 'react'; export default function TestComponent() { const [testTools, setTestTools] = useState(null); // 仅在客户端加载jest-lite useEffect(() => { async function loadJestLite() { // 如果直接导入报错,试试导入dist文件:import('jest-lite/dist/jest-lite') const { describe, it, expect, run } = await import('jest-lite'); setTestTools({ describe, it, expect, run }); } loadJestLite(); }, []); // 工具加载完成后执行测试 useEffect(() => { if (!testTools) return; const { describe, it, expect, run } = testTools; describe('页面功能测试', () => { it('基础逻辑验证', () => { expect(true).toBeTruthy(); }); }); run(); }, [testTools]); return ( <div> {testTools ? <p>测试执行中...</p> : <p>加载测试工具中...</p>} </div> ); }
解决Can't resolve 'jest-lite'错误
- 调整依赖安装位置:确保jest-lite在
dependencies中(生产构建不会安装devDependencies):npm uninstall jest-lite --save-dev npm install jest-lite --save - 修正导入路径:部分版本的jest-lite需要直接导入编译后的dist文件,将
import('jest-lite')替换为import('jest-lite/dist/jest-lite')。
注意事项
- 所有调用jest-lite方法的代码,必须放在客户端执行的逻辑中(比如
useEffect、动态导入的回调里),不能在组件顶层直接执行。 - 若测试代码较多,可以封装到单独的客户端模块,再通过上述方式导入。
内容的提问来源于stack exchange,提问作者lauren_d
相关产品推荐
相关产品推荐

