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

Next.js + Jest路由匹配测试:MenuItem组件分支覆盖率问题

单元测试分支未覆盖问题:MenuItem组件selected类分支无法覆盖

背景

我正在对组件进行单元测试以实现100%代码覆盖率,但以下MenuItem组件存在一个分支未被覆盖。为更清晰说明,以下是渲染它的父组件代码。

"use client";

import menu from "@/data/menu.json";
import { usePathname } from "next/navigation";
import React, { useState } from "react";
import styles from "./styles.module.css";
import MenuItem from "../MenuItem";
import { RxHamburgerMenu } from "react-icons/rx";
import MenuModal from "@/modals/MenuModal";

const Menu: React.FC = () => {
  const pathname = usePathname();
  const [isMenuModalVisible, setMenuModalVisibliity] = useState(false);

  const toggleMenuModal = () =>
    setMenuModalVisibliity((prevState) => !prevState);

  return (
    <nav>
      <RxHamburgerMenu
        onClick={toggleMenuModal}
        size={24}
        className={styles.hamburgerMenu}
        data-testid="hamburger-menu-icon"
      />
      <ul className={styles.wrapper}>
        {menu.map((item) => {
          return <MenuItem key={item.id} {...item} pathname={pathname} />;
        })}
      </ul>
      {isMenuModalVisible && <MenuModal onClose={toggleMenuModal} />}
    </nav>
  );
};

export default Menu;

import Link from "next/link";
import { memo } from "react";
import styles from "./styles.module.css";

interface MenuItemProps {
  id: string;
  label: string;
  href: string;
  pathname: string;
}

const MenuItem: React.FC<MenuItemProps> = ({ href, label, pathname }) => {
  return (
    <li>
      <Link
        href={href}
        data-testid="menu-item"
        className={pathname === href ? styles.selected : undefined}
      >
        {label}
      </Link>
    </li>
  );
};

export default memo(MenuItem);

我编写的测试代码如下:

import MenuItem from "@/components/MenuItem";
import { render, screen } from "@testing-library/react";
import { usePathname } from "next/navigation";

describe("MenuItem", () => {
  it("should render successfully", async () => {
    const { container } = render(
      <MenuItem href="/" id="home" label="Home" pathname="/" />
    );
    const menuItem = await screen.findByTestId("menu-item");

    expect(menuItem).toHaveClass("selected");
    expect(container).toMatchSnapshot();
  });

  it("should render successfully without the selected class", async () => {
    const { container } = render(
      <MenuItem href="/about-us" id="home" label="Home" pathname="/" />
    );
    const menuItem = await screen.findByTestId("menu-item");

    expect(menuItem).not.toHaveClass("selected");
    expect(container).toMatchSnapshot();
  });
});

未覆盖的分支

pathname === href ? styles.selected 中的相关分支(覆盖率提示显示href ? styles.selected未被覆盖)

遇到的问题

我尝试mock next/navigation库和usePathname钩子,但始终无法覆盖该分支。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.24 17:53:11