Skip to content
Skills Library
Programming · Testing

testing

/testing

Apply when writing .test.ts or .test-d.ts files. Esposter's Vitest conventions and the decision of what earns a test at all. The values a test writes are the test-values skill's.

Repository
Esposter ↗
Licence
Apache-2.0
Last repository change
26.10.2026

Assessment and security

90/ 100Class: good
Format25 / 25
Frontmatter with name and description, valid name, description up to 1,024 characters, name matching the folder.
Discoverability25 / 25
Description explains when to use the skill, has a reasonable length and uses third person.
Content25 / 35
At least 150 words and at most 500 lines, headings, step lists, examples or code.
Hygiene15 / 15
No placeholders such as TODO, no Windows paths, with a licence.
Riskno signals detected in the scan
Files in this package
28
Scripts
0
HTML comments
0
URLs in SKILL.md
0
Deprecation

No signals detected. Repository changed on 26.10.2026, without references to retired models or APIs.

Licence

Apache-2.0, otwarta: można używać i zmieniać, z zachowaniem licencji i informacji o zmianach.

What it does and when to use it

Apply when writing .test.ts or .test-d.ts files. Esposter's Vitest conventions and the decision of what earns a test at all. The values a test writes are the test-values skill's.

Original author description

Apply when writing .test.ts or .test-d.ts files. Esposter's Vitest conventions and the decision of what earns a test at all. The values a test writes are the test-values skill's.

How it works

  1. Settled — do not re-propose
  2. Deep dives
  3. Structure
  4. Test data — the test-values skill
  5. Assertions
  6. Mocking
  7. Reactive Effects and Timers
  8. Running Tests
  9. What to Test
Original SKILL.md headings · 102 lines, 1,389 words
SKILL.md preview
---
name: testing
description: Apply when writing .test.ts or .test-d.ts files. Esposter's Vitest conventions and the decision of what earns a test at all. The values a test writes are the test-values skill's.
---

# Testing Conventions (Vitest)

## Settled — do not re-propose

- **A lint rule for constant scope** — an AST selector cannot ask the two whole-Program questions the exceptions turn on (a helper file, a binding read from a hoisted `vi.mock` factory or an awaited initialiser); `scripts/src/workspace/constantScope.test.ts` is the enforcer and asks both.
- **`isolate: false`, per project or globally.** The packages that survive it come out level, and the apparent gain belongs to the ones that fail under it for the reason isolation exists (`references/running-the-suite.md`).
- **A count target for tests** — a cap or quota per package measures how many tests exist, not whether a regression is caught. The keep test in `references/what-earns-a-test.md` is the only gate on a test.

## Deep dives

Structure and helpers:

- `references/what-earns-a-test.md` — when deciding whether a subject earns a test at all, and which one.
- `references/test-placement.md` — when deciding which file a test goes in, or whether two checks over one directory are one suite.
- `references/suite-titles.md` — when a `describe`'s subject has no function reference, or its export is not camelCase.
- `references/module-scope.md` — when a test declares anything outside its `describe`, or `constantScope.test.ts` reports one.
- `references/case-tables.md` — when a test runs over a table of cases.
- `references/test-helper-files.md` — when a helper, fixture or hook block is shared between suites: one function per file, `constants.test.ts`, `setup*` fixtures.
- `references/wrapper-suites.md` — when two suites match modulo constants, or a suite tests a thin wrapper.
- `references/type-tests.md` — when writing a `.test-d.ts`, or asserting a `void` return.
- `references/router-test-setup.md` — when writing a tRPC router test: callers, mock sessions, seeded rows, naming.

Assertions and waiting:

- `references/assertions.md` — when writing a test's `expect` calls: the matcher, how much of the value, a void return, a call's arguments.
- `references/error-assertions.md` — when filling in the inline snapshot a thrown or rejected error is asserted with.
- `references/polling.md` — when a test waits for something to happen.
- `references/timers-and-hand-resolved-promises.md` — when a test fakes timers, pins the clock, or holds a call in flight.
- `references/awaiting-a-double.md` — when a test proves a caller awaits its side effect, orders two overlapping calls, or reads what a tRPC call caused.

Doubles:

- `references/module-mocks.md` — when reaching for `vi.mock` or a spy: whether the behaviour needs a double, and which seam.
- `references/colocated-mocks.md` — when a module is mocked in several suites, writing a `vi.mock` factory, or mocking `db` or a `Proxy` export.
- `references/client-trpc-calls.md` — when code under test calls tRPC from the client: `setupMswTrpc` and `trpcMsw`, never a mocked client.
- `references/mock-cleanup.md` — when choosing a mock's cleanup hook, queuing once-values, or stubbing a global or env var.
- `references/fabricated-ids.md` — when a mock returns a persisted entity, or a new foreign key turns a suite red.

Environment and running:

- `references/test-environment.md` — when a test needs a DOM, a layout engine or the nuxt runtime, or tests a composable with lifecycle hooks.
- `references/nuxt-environment-and-mounting.md` — when a test mounts a component: a routed link, a mount attached to the body, a dispatched event.
- `references/mounted-stores.md` — when a test seeds a store a mounted component reads, room-scoped stores included, or a suite reaches for its own Pinia.
- `references/platform-and-bundle-tests.md` — when a suite is skipped on some hosts, or its output depends on the host.
- `references/bundle-size.md` — when a size snapshot fails or moves, or a new library package needs one.
- `references/running-the-suite.md` — when narrowing a run with `-t` or `-u`, or reading a failure only the full parallel run produces.
- `references/timeouts.md` — when a test, suite or config sets a timeout, or a test fails with `Test timed out`: the measurement and the ladder that decide whether a timeout is earned at all.
- `references/regression-proof.md` — when a regression test is about to be kept, and its fix is reverted for the end-of-work run.

## Structure

- **`test` not `it`** — always `test(...)`.
- **A test lives beside what it tests** — `Foo.ts` → `Foo.test.ts`, never folded into a nearby suite or moved to the module it scans (`references/test-placement.md`).
- **A file snapshot lives beside what it holds, as `<name>.snapshot.<extension>`** — a component's rendered HTML beside the component, a parsed map beside the map — never in a `__snapshots__` folder. The suffix is what the formatter and the JSON lint skip, so the file stays as its test wrote it.
- **`describe(functionRef, …)`**, flat — a string only when no reference exists, naming the file's export; `describe.each` over a matrix is not a group (`references/suite-titles.md`).
- **Nothing but imports, pure helpers and hoisted mocks lives at module scope** — every constant is a `const` inside the `describe` (`references/module-scope.md`).
- **`test.each` for a table of cases, never a loop around `test`** (`vitest/prefer-each`), titled with `%s` (`references/case-tables.md`).
- **`expect.hasAssertions()`** — top of every test body.
- **Assertions after all assignments** — `expect` calls follow that phase's operations and locals, after a blank line.
- **A `void` return is never assigned or asserted at runtime** — `await fn();` bare, or `resolves.toBeUndefined()` (`references/assertions.md`).
- **Reuse utilities, and prefix factories `create*`** — look for an existing helper beside the code under test first; builders are `createRow`, never `make*`.

## Test data — the `test-values` skill

Every literal, id, date, path and fixture a test writes is that skill's: the canonical values, dates computed from the epoch, the three checks a string literal passes, and the shared-data shapes. This page assumes them.

## Assertions

- **`toStrictEqual` always**, exact counts, and `arrayContaining` never for an argv or an ordered sequence (`references/assertions.md`).
- **Never fragment-match a deterministic output** — the whole value with `.toBe(...)` or an inline snapshot, a runtime value the test holds interpolated in, never an element sampled from a knowable sequence (`references/assertions.md`).
- **Once + args → `toHaveBeenCalledExactlyOnceWith(...)`**, never the jest-extended once-with matcher (`references/assertions.md`).
- **`takeOne(arr, index)`** for `arr[index]` under `noUncheckedIndexedAccess` — not universal, prefer `find` when more idiomatic. **`assert.exists(value)`** narrows nullables and fails fast instead of `?? []`. Cloning: the `typescript` skill (`references/cloning.md`).
- **No unnecessary destructure** — for plain objects, read a property directly when used once. Stores and composables keep the destructure ordering of the `pinia` skill's `references/consuming-a-store.md`, unchanged in tests.
- **`toThrowErrorMatchingInlineSnapshot(...)` is the only accepted error assertion**, sync and async (`vitest/no-restricted-matchers`); `not.toThrow()` is not an error assertion and stays, as how a best-effort function proves it swallows what it should (`references/error-assertions.md`).

## Mocking

- **Mock the smallest seam that makes the behaviour reachable**, never re-declare a mock another file owns, and drive real state before faking it (`references/module-mocks.md`).
- **The cleanup hook follows how the mock was created**, never habit — the wrong one leaks an implementation or a queued once-value into the next test (`references/mock-cleanup.md`).
- **`vi.fn()` always takes its signature** — `vi.fn<(input: CreateEmojiInput) => Promise<void>>()`, the production input and return types imported rather than restated. A bare `vi.fn()` infers `unknown` parameters, so destructuring a recorded call is an implicit-`any` lint error and `mockResolvedValue` accepts anything.

## Reactive Effects and Timers

- **A `watch` callback and a re-render run on Vue's scheduler, never synchronously** — `await nextTick()` flushes them after the write that queued them; `flushPromises()` from `@vue/test-utils` when the callback itself awaits. With nothing queued, neither is written.
- **Fake timers, and any promise the test resolves by hand, follow `references/timers-and-hand-resolved-promises.md`** — one `vi.useFakeTimers({ now: 0 })` in `beforeEach` with an unconditional restore in `afterEach`, `toFake` narrowed rather than widened, and `Promise.withResolvers` instead of a `let` closed over by an executor.
- **Await the real completion signal, never a poll** — the repo-wide ban is `openspec/specs/architecture/no-polling/design.md`, and the test forms are `references/polling.md`.

## Running Tests

- **The touched tests are a session's one check, run in the background once at the end** — the rest are CI's (the `running-checks` skill).
- **Never run the full suite locally** — `pnpm test <paths> --run` over what the change touched (`references/running-the-suite.md`).
- **`-t "name"` is not a scope, and `-u` gets the narrowest path list** — read the snapshot diff before committing (`references/running-the-suite.md`).

## What to Test

**Every test earns its line or it is deleted** — the keep test in `references/what-earns-a-test.md` decides it.

- **A regression test is proven to fail before it is kept** — the end-of-work run that shows it is `references/regression-proof.md`.

- What never earns a line, and the subjects already decided: `references/what-earns-a-test.md`.
Files in this package (28)
  • SKILL.md 10 KB
  • references/assertions.md 4 KB
  • references/awaiting-a-double.md 4 KB
  • references/bundle-size.md 4 KB
  • references/case-tables.md 1 KB
  • references/client-trpc-calls.md 4 KB
  • references/colocated-mocks.md 7 KB
  • references/error-assertions.md 3 KB
  • references/fabricated-ids.md 2 KB
  • references/mock-cleanup.md 3 KB
  • references/module-mocks.md 1 KB
  • references/module-scope.md 2 KB
  • references/mounted-stores.md 3 KB
  • references/nuxt-environment-and-mounting.md 4 KB
  • references/platform-and-bundle-tests.md 3 KB
  • references/polling.md 1 KB
  • references/regression-proof.md 1 KB
  • references/router-test-setup.md 5 KB
  • references/running-the-suite.md 6 KB
  • references/suite-titles.md 2 KB
  • references/test-environment.md 4 KB
  • references/test-helper-files.md 4 KB
  • references/test-placement.md 1 KB
  • references/timeouts.md 3 KB
  • references/timers-and-hand-resolved-promises.md 5 KB
  • references/type-tests.md 1 KB
  • references/what-earns-a-test.md 7 KB
  • references/wrapper-suites.md 2 KB

Versions

RepositoryScoreLicence
This page · Esposter/Esposter90Apache-2.0
iuliandita/skills100MIT
wrongstack/wrongstack100MIT
langwatch/langwatch100Apache-2.0
mcouthon/agents100MIT
nteract/nteract100BSD-3-Clause
kettleofketchup/DraftForge100GPL-3.0
skillberry-ai/cap-evolve100Apache-2.0
TheBeardedBearSAS/claude-craft100MIT

Database snapshot: 13.11.2026 · package version 0f6d494a4356 (SHA-256 digest of the entire package)

Downloads in the last 30 days: 0 · ranking

Report a problem with this skill: harmful content, incorrect descriptions or an author’s removal request.

Similar skills

  • 90typescript
    Apply when writing any TypeScript in this project. Esposter's TypeScript conventions.
  • 90test-values
    Apply when writing or reviewing any literal, fixture, id, date, path or helper argument in a .test.ts, .test-d.ts or .bench.ts file. Esposter's test values — the literals, ids, dates, paths and fixtures a test writes, and the shared data they are drawn from.
  • 92conventions-testing
    Apply when writing or reviewing tests.
  • 100vitest
    Vitest conventions for assertions, snapshots, and fixtures. Use when writing, reviewing, or fixing Vitest tests.
  • 100vitest-test-creator
    Create vitest test creator operations. Auto-activating skill for Test Automation. Triggers on: vitest test creator, vitest test creator Part of the Test Automation skill category. Use when writing or running tests. Trigger with phrases like "vitest test creator", "vitest creator", "vitest".
  • 100react-testing
    Test React components with RTL and Jest/Vitest. Use when writing React component tests with React Testing Library, Jest, or Vitest.

Feedback and reports

Your message goes to Bartosz Sokoliński. An email address is needed only for a reply. See the privacy policy.