write-tests

GitHub

提供Web UI单元测试编写指南,涵盖Vitest+RTL配置、文件布局及针对上下文依赖代码的测试模式。

webui/.agents/skills/write-tests/SKILL.md eclipse-openvsx/openvsx

Trigger Scenarios

需要为前端组件或逻辑编写单元测试 询问如何配置Vitest和React Testing Library环境 需要处理带有路由或Provider依赖的前端测试场景

Install

npx skills add eclipse-openvsx/openvsx --skill write-tests -g -y
More Options

Non-standard path

npx skills add https://github.com/eclipse-openvsx/openvsx/tree/main/webui/.agents/skills/write-tests -g -y

Use without installing

npx skills use eclipse-openvsx/openvsx@write-tests

指定 Agent (Claude Code)

npx skills add eclipse-openvsx/openvsx --skill write-tests -a claude-code -g -y

安装 repo 全部 skill

npx skills add eclipse-openvsx/openvsx --all -g -y

预览 repo 内 skill

npx skills add eclipse-openvsx/openvsx --list

SKILL.md

Frontmatter
{
    "name": "write-tests",
    "description": "How to write unit tests for the webui — the vitest + React Testing Library setup, file layout, harness patterns for context\/router-dependent code, and the fail-first check that proves a test actually guards its target. Use when adding or updating tests under test\/unit."
}

Writing unit tests (webui)

Stack

  • vitest (yarn test runs vitest run), jsdom environment, React Testing Library (@testing-library/react, @testing-library/user-event, @testing-library/jest-dom).
  • Config: vite.config.mtstest.include: ['test/unit/**/*.spec.{ts,tsx}'], setupFiles: ['./test/setup.ts'].
  • test/setup.ts registers jest-dom matchers and an afterEach(cleanup). Vitest globals are off: import describe/it/expect/vi from 'vitest', and don't add your own RTL cleanup — setup.ts owns it.

Layout

  • Mirror the source path under test/unit/ (e.g. src/context/search/…test/unit/context/…).
  • Reusable harnesses/mocks go in test/unit/support/.

Test what you own, not your dependencies

Assert the logic and wiring that belong to this codebase — not behavior a dependency already guarantees. A test whose only assertion is that MUI Tabs switch tabs, react-router navigates, or TanStack caches is testing someone else's library; it earns nothing and breaks on their upgrades.

  • Exercising that behavior incidentally, as a step in a flow that asserts your own logic, is good — click the tab, then assert the panel your code renders. What you don't do is write a dedicated test for the third-party behavior alone.
  • When you catch yourself asserting a library did its job, move the assertion to the part you own: the props you passed it, the state/callback you wired, the value you derived from its output.

Patterns, simplest first

  • Pure functions → call and assert. See test/unit/utils.spec.ts.
  • Componentsrender + screen + jest-dom matchers (toBeInTheDocument, …). See test/unit/components/kbd-key.spec.tsx. Prefer @testing-library/user-event for real interaction over synthetic events.
  • Anything that needs the app's providers (a TanStack hook reading service from MainContext, a component using search, keyboard shortcuts, the theme, or routing) → render it through the shared harness test/unit/support/test-providers.tsx: renderWithProviders(ui, { route, mainContext: { service } }) for components, renderHookWithProviders(hook, …) for hooks (the idiomatic way to read a hook's return via result.current), or withProviders(Component, opts) for the HOC form. The harness reuses the app's real AppProviders (so it tracks the app automatically — query client, MainContext, keyboard shortcuts, search) and adds the entry-shell bits AppProviders doesn't own (a fresh no-retry QueryClient, the MUI theme, a MemoryRouter). Reach for this first — don't hand-roll a provider stack per spec.
  • Routing / history → don't mock it. test-providers mounts a real MemoryRouter; drive back/forward with the useNavigate() you pull from the hook under test (navigate(-1) / navigate(1) are POPs), and pass the starting URL via route.
  • An external dependency whose timing or return you must control (a slow client, a flaky global) → vi.mock('pkg', …) it with a small controllable stand-in, kept generic and reusable in test/unit/support/. Reach for this only when the real thing genuinely can't be driven — prefer the real router/providers first.

Grow the harness, don't duplicate it

The suite gets easier to extend only if shared test code is treated like production code.

  • Before writing a mock, stub, or render helper, check test/unit/support/ for one that already fits and reuse it.
  • If an existing helper almost fits, extend or refactor it — kept generic and dependency-agnostic — rather than forking a near-duplicate. A second caller is the signal to generalize, not to copy.
  • When an inline mock or helper in a spec would help another test, promote it to test/unit/support/ before it gets copied.
  • Refactoring a shared harness is part of adding the test that needs it: update every call site and leave the whole suite green. Never let two helpers do the same job.
  • Don't write tests for the test helpers themselves. A harness or mock in test/unit/support/ is exercised by the specs that use it; it never gets its own spec.

The fail-first check (required for regression tests)

A test that passes tells you nothing until you've seen it fail. After writing a test that guards a fix, temporarily break the code it protects, run the test, confirm it goes red, then restore. This is the only thing that proves the test is wired to the behavior — it matters most for timing/race fixes, where a naive test passes with or without the fix.

Run

  • One file while iterating: yarn vitest run test/unit/<path>.spec.tsx.
  • Whole suite: yarn test. Iterate on test or implementation until green, then yarn lint.

Version History

  • 4c33308 Current 2026-08-20 15:10

Same Skill Collection

webui/.agents/skills/migrate-to-tanstack/SKILL.md
webui/.agents/skills/tanstack-query-conventions/SKILL.md
webui/.agents/skills/write-code/SKILL.md

Metadata

Files
0
Version
4c33308
Hash
6366d600
Indexed
2026-08-20 15:10

- 위키
Copyright © 2011-2026 iteam. Current version is 2.155.2. UTC+08:00, 2026-08-25 13:30
浙ICP备14020137号-1 $방문자$