> ## Documentation Index
> Fetch the complete documentation index at: https://docs.meow.style/llms.txt
> Use this file to discover all available pages before exploring further.

# Testing

> An isolate-backed, deterministic test runner with a built-in expect API — no test framework to install.

meow has a test runner built in. Each test file runs in its own **deterministic V8
isolate**, so suites can't leak state into each other and every run is reproducible
by construction.

```bash theme={null}
meow test
```

## Writing tests

Import the API from the [`meow:test`](/api/test) built-in module. There's nothing
to install.

```typescript math.test.ts theme={null}
import { test, expect } from "meow:test";

test("adds", () => {
  expect(2 + 2).toBe(4);
});

test("builds the right shape", () => {
  expect({ ok: true }).toEqual({ ok: true });
});

test("throws on bad input", () => {
  expect(() => JSON.parse("{")).toThrow();
});
```

### Discovery

`meow test` walks the project and runs every file whose name ends in **`.test.`**
or **`.spec.`** with a JS/TS extension (`.ts`, `.tsx`, `.js`, `.jsx`, `.mts`,
`.mjs`, `.cts`, `.cjs`). It skips `node_modules`, `target`, `vendor`, and hidden
directories.

### Matchers

The `expect()` API covers the essentials, each with a `.not` inverse:

| Matcher                        | Passes when                                            |
| ------------------------------ | ------------------------------------------------------ |
| `toBe(v)`                      | `Object.is(actual, v)` (identity / primitive equality) |
| `toEqual(v)`                   | deep structural equality                               |
| `toBeNull()`                   | value is `null`                                        |
| `toBeDefined()`                | value is not `undefined`                               |
| `toBeTruthy()` / `toBeFalsy()` | truthiness                                             |
| `toThrow()`                    | calling the function throws                            |
| `.not`                         | inverts any of the above                               |

```typescript theme={null}
expect(user.name).not.toBe("");
```

## Output

```text theme={null}
math.test.ts
  ✓ adds
  ✓ builds the right shape
  ✓ throws on bad input
╭─ meow test ─────────────────────────────────╮
│ 🐾 3 passed · 1 file                          │
╰──────────────────────────────────────────────╯
```

A failure shows the assertion and the first stack line, and the runner exits
non-zero:

```text theme={null}
sum.test.ts
  ✗ adds
    expect(5).toBe(4)
╭─ meow test ─────────────────────────────────╮
│ ✗ 0 passed, 1 failed · 1 file                 │
╰──────────────────────────────────────────────╯
```

## Determinism is the default

<Note>
  Tests always run in a **deterministic strict-web isolate**, no matter your
  project [mode](/concepts/modes). The clock is frozen, randomness is seeded, and the
  timezone is pinned — so time- and random-dependent tests are stable instead of
  flaky. If a test genuinely needs real time or host access, that's a deliberate
  grant, not the default.
</Note>

Because each file gets a fresh isolate, there's no shared global state to reset
between files and no cross-test contamination.

<Card title="The meow:test API" icon="vial" href="/api/test">
  Full type signatures for test() and expect().
</Card>
