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

多项目场景下使用nextJest遇JSX编译失败问题求助

Next.js多项目Jest配置中nextJest不生效的问题解决

问题场景

我使用以下jest.config.ts配置时,后端测试正常,但前端JSX编译失败:

import type { Config } from "jest";
import nextJest from "next/jest.js";

const createJestConfig = nextJest({ dir: "./" });

const config: Config = {
  projects: [
    {
      displayName: "backend",
      testMatch: ["<rootDir>/tests/**/*.test.ts"],
      testEnvironment: "node",
      clearMocks: true,
      preset: "ts-jest",
      globalSetup: "<rootDir>/tests/globalSetup.ts",
      moduleNameMapper: {
        "^@/(.*)$": "<rootDir>/src/$1",
      },
    },
    {
      displayName: "frontend",
      testMatch: ["<rootDir>/src/**/*.test.{ts,tsx}"],
      testEnvironment: "jsdom",
      clearMocks: true,
      preset: "ts-jest",
      setupFilesAfterEnv: ["<rootDir>/src/jest.setup.ts"],
      moduleNameMapper: {
        "^@/(.*)$": "<rootDir>/src/$1",
      },
    },
  ],
};

export default createJestConfig(config);

排查后发现,单独配置前端时(如下)就能正常运行,说明nextJest对配置的修改并未作用到projects数组中的子配置:

import type { Config } from "jest";
import nextJest from "next/jest.js";

const createJestConfig = nextJest({ dir: "./" });

const config: Config = {
  displayName: "frontend",
  testMatch: ["<rootDir>/src/**/*.test.{ts,tsx}"],
  testEnvironment: "jsdom",
  clearMocks: true,
  preset: "ts-jest",
  setupFilesAfterEnv: ["<rootDir>/src/jest.setup.ts"],
  moduleNameMapper: {
    "^@/(.*)$": "<rootDir>/src/$1",
  },
};

export default createJestConfig(config);

想找到既能继续使用nextJest,又不用手动复制生成配置的解决方案。

可行解决方案

方案1:对前端子配置单独应用nextJest

nextJest的createJestConfig函数只会处理顶层配置,不会递归处理projects里的子项。因此可以单独给前端配置调用createJestConfig,后端配置保持原生Jest配置即可:

import type { Config } from "jest";
import nextJest from "next/jest.js";

// 初始化前端专用的nextJest配置生成器
const createFrontendJestConfig = nextJest({ dir: "./" });

// 后端配置直接定义,无需经过nextJest处理
const backendConfig: Config = {
  displayName: "backend",
  testMatch: ["<rootDir>/tests/**/*.test.ts"],
  testEnvironment: "node",
  clearMocks: true,
  preset: "ts-jest",
  globalSetup: "<rootDir>/tests/globalSetup.ts",
  moduleNameMapper: {
    "^@/(.*)$": "<rootDir>/src/$1",
  },
};

// 用nextJest处理前端配置,注意这里需要异步调用
const frontendConfig = await createFrontendJestConfig({
  displayName: "frontend",
  testMatch: ["<rootDir>/src/**/*.test.{ts,tsx}"],
  testEnvironment: "jsdom",
  clearMocks: true,
  preset: "ts-jest",
  setupFilesAfterEnv: ["<rootDir>/src/jest.setup.ts"],
  moduleNameMapper: {
    "^@/(.*)$": "<rootDir>/src/$1",
  },
});

// 组合两个项目配置导出
export default {
  projects: [backendConfig, frontendConfig],
};

注意:Jest支持异步配置,所以这里可以直接用await,不需要额外包装成Promise。

方案2:手动同步nextJest的核心配置(不推荐)

如果不想拆分配置,可以手动复现nextJest的核心转换逻辑,主要包括:

  • 添加transform规则,用Next.js的转译器处理TSX/JSX文件
  • 补充静态资源的moduleNameMapper(比如图片、CSS、字体等)
  • 注入Next.js的环境变量和测试环境配置

但这种方式需要手动维护配置,一旦Next.js版本更新,可能需要同步修改,容易出错,因此优先推荐方案1。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.14 07:17:03