Skip to content

Commit

Permalink
chore: more docs and cleanup
Browse files Browse the repository at this point in the history
  • Loading branch information
sheremet-va committed Oct 2, 2022
1 parent bc509c0 commit ffd1377
Show file tree
Hide file tree
Showing 8 changed files with 157 additions and 11 deletions.
4 changes: 4 additions & 0 deletions docs/.vitepress/config.ts
Expand Up @@ -115,6 +115,10 @@ export default defineConfig({
text: 'Features',
link: '/guide/features',
},
{
text: 'Testing Types',
link: '/guide/testing-types',
},
{
text: 'CLI',
link: '/guide/cli',
Expand Down
59 changes: 56 additions & 3 deletions docs/api/index.md
Expand Up @@ -72,6 +72,10 @@ In Jest, `TestFunction` can also be of type `(done: DoneCallback) => void`. If t
})
```

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

### test.runIf

- **Type:** `(condition: any) => Test`
Expand All @@ -89,6 +93,10 @@ In Jest, `TestFunction` can also be of type `(done: DoneCallback) => void`. If t
})
```

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

### test.only

- **Type:** `(name: string, fn: TestFunction, timeout?: number) => void`
Expand Down Expand Up @@ -152,6 +160,10 @@ In Jest, `TestFunction` can also be of type `(done: DoneCallback) => void`. If t
})
```

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

### test.todo

- **Type:** `(name: string) => void`
Expand Down Expand Up @@ -179,6 +191,10 @@ In Jest, `TestFunction` can also be of type `(done: DoneCallback) => void`. If t
})
```

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

### test.each
- **Type:** `(cases: ReadonlyArray<T>) => void`
- **Alias:** `it.each`
Expand Down Expand Up @@ -210,8 +226,29 @@ In Jest, `TestFunction` can also be of type `(done: DoneCallback) => void`. If t
// ✓ add(2, 1) -> 3
```

You can also access object properties with `$` prefix, if you are using objects as arguments:

```ts
test.each([
{ a: 1, b: 1, expected: 2 },
{ a: 1, b: 2, expected: 3 },
{ a: 2, b: 1, expected: 3 },
])('add($a, $b) -> $expected', ({ a, b, expected }) => {
expect(a + b).toBe(expected)
})

// this will return
// ✓ add(1, 1) -> 2
// ✓ add(1, 2) -> 3
// ✓ add(2, 1) -> 3
```

If you want to have access to `TestContext`, use `describe.each` with a single test.

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

## bench

- **Type:** `(name: string, fn: BenchFunction, options?: BenchOptions) => void`
Expand Down Expand Up @@ -472,6 +509,10 @@ When you use `test` or `bench` in the top level of file, they are collected as p
describe.todo.concurrent(/* ... */) // or describe.concurrent.todo(/* ... */)
```

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

### describe.shuffle

- **Type:** `(name: string, fn: TestFunction, options?: number | TestOptions) => void`
Expand All @@ -489,6 +530,10 @@ When you use `test` or `bench` in the top level of file, they are collected as p

`.skip`, `.only`, and `.todo` works with random suites.

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

### describe.todo

- **Type:** `(name: string) => void`
Expand Down Expand Up @@ -526,6 +571,10 @@ When you use `test` or `bench` in the top level of file, they are collected as p
})
```

::: warning
You cannot use this syntax, when using Vitest as [type checker](/guide/testing-types).
:::

## expect

- **Type:** `ExpectStatic & (actual: any) => Assertions`
Expand All @@ -547,6 +596,10 @@ When you use `test` or `bench` in the top level of file, they are collected as p

Also, `expect` can be used statically to access matchers functions, described later, and more.

::: warning
`expect` has no effect on testing types, if expression doesn't have a type error. If you want to use Vitest as [type checker](/guide/testing-types), use [`expectTypeOf`](#expecttypeof) or [`assertType`](#asserttype).
:::

### not

Using `not` will negate the assertion. For example, this code asserts that an `input` value is not equal to `2`. If it's equal, assertion will throw an error, and the test will fail.
Expand Down Expand Up @@ -1778,7 +1831,7 @@ When you use `test` or `bench` in the top level of file, they are collected as p

## Setup and Teardown

These functions allow you to hook into the life cycle of tests to avoid repeating setup and teardown code. They apply to the current context: the file if they are used at the top-level or the current suite if they are inside a `describe` block.
These functions allow you to hook into the life cycle of tests to avoid repeating setup and teardown code. They apply to the current context: the file if they are used at the top-level or the current suite if they are inside a `describe` block. These hooks are not called, when you are running Vitest as type checker.

### beforeEach

Expand Down Expand Up @@ -1970,9 +2023,9 @@ Vitest provides utility functions to help you out through it's **vi** helper. Yo

- **Type**: `(path: string, factory?: () => unknown) => void`

Makes all `imports` to passed module to be mocked. Inside a path you _can_ use configured Vite aliases.
Makes all `imports` to passed module to be mocked. Inside a path you _can_ use configured Vite aliases. The call to `vi.mock` is hoisted, so it doesn't matter where you call it. It will always be executed before all imports.

- If `factory` is defined, will return its result. Factory function can be asynchronous. You may call [`vi.importActual`](#vi-importactual) inside to get the original module. The call to `vi.mock` is hoisted to the top of the file, so you don't have access to variables declared in the global file scope!
- If `factory` is defined, will return its result. Factory function can be asynchronous. You may call [`vi.importActual`](#vi-importactual) inside to get the original module. Since the call to `vi.mock` is hoisted, you don't have access to variables declared in the global file scope!
- If mocking a module with a default export, you'll need to provide a `default` key within the returned factory function object. This is an ES modules specific caveat, therefore `jest` documentation may differ as `jest` uses commonJS modules. *Example:*

```ts
Expand Down
55 changes: 55 additions & 0 deletions docs/config/index.md
Expand Up @@ -849,3 +849,58 @@ Vitest usually uses cache to sort tests, so long running tests start earlier - t
- **Default**: `Date.now()`

Sets the randomization seed, if tests are running in random order.

### typechecker

Options for configuring [typechecking](/guide/testing-types) test environment.

#### typechecker.checker

- **Type**: `'tsc' | 'vue-tsc' | string`
- **Default**: `tsc`

What tools to use for type checking. Vitest will spawn a process with certain parameters for easier parsing, depending on the type. Checker should implement the same output format as `tsc`.

You need to have a package installed to use typecheker:

- `tsc` requires `typescript` package
- `vue-tsc` requires `vue-tsc` package

You can also pass down a path to custom binary or command name that produces the same output as `tsc --noEmit --pretty false`.

#### typechecker.include

- **Type**: `string[]`
- **Default**: `['**/*.{test,spec}-d.{ts,js}']`

Glob pattern for files that should be treated as test files

#### typechecker.exclude

- **Type**: `string[]`
- **Default**: `['**/node_modules/**', '**/dist/**', '**/cypress/**', '**/.{idea,git,cache,output,temp}/**']`

Glob pattern for files that should not be treated as test files

#### typechecker.allowJs

- **Type**: `boolean`
- **Default**: `false`

Check JS files that have `@ts-check` comment. If you have it enabled in tsconfig, this will not overwrite it.

#### typechecker.ignoreSourceErrors

- **Type**: `boolean`
- **Default**: `false`

Do not fail, if Vitest found errors outside the test files. This will not show you non-test errors at all.

By default, if Vitest finds source error, it will fail test suite.

#### typechecker.tsconfig

- **Type**: `string`
- **Default**: _tries to find closest tsconfig.json_

Path to custom tsconfig, relative to the project root.
28 changes: 28 additions & 0 deletions docs/guide/testing-types.md
@@ -0,0 +1,28 @@
---
title: Testing Types | Guide
---

# Testing Types

Vitest allows you to write tests for your types.

Under the hood Vitest calls `tsc` or `vue-tsc`, depending on your config, and parses results.

```ts
// TODO write normal tests examples
import { describe, expectTypeOf, test } from 'vitest'

describe('test', () => {
test('some-test', () => {
expectTypeOf(45).toBe(45)
})

describe('test2', () => {
test('some-test 2', () => {
expectTypeOf(45).toBe(45)
})
})
})

expectTypeOf({ wolk: 'true' }).toHaveProperty('wolk')
```
2 changes: 1 addition & 1 deletion packages/vitest/src/defaults.ts
Expand Up @@ -91,7 +91,7 @@ const config = {
dangerouslyIgnoreUnhandledErrors: false,
typecheck: {
checker: 'tsc' as const,
include: ['**/*.test-d.ts'],
include: ['**/*.{test,spec}-d.{ts,js}'],
exclude: defaultExclude,
},
}
Expand Down
6 changes: 3 additions & 3 deletions packages/vitest/src/types/config.ts
Expand Up @@ -452,9 +452,9 @@ export interface InlineConfig {

export interface TypecheckConfig {
/**
* What tool to use for type checking.
* What tools to use for type checking.
*/
checker: 'tsc' | 'vue-tsc'
checker: 'tsc' | 'vue-tsc' | (string & Record<never, never>)
/**
* Pattern for files that should be treated as test files
*/
Expand All @@ -469,7 +469,7 @@ export interface TypecheckConfig {
*/
allowJs?: boolean
/**
* Do not fail, if Vitest found errors not inside the test files.
* Do not fail, if Vitest found errors outside the test files.
*/
ignoreSourceErrors?: boolean
/**
Expand Down
4 changes: 2 additions & 2 deletions packages/vitest/src/typescript/collect.ts
Expand Up @@ -80,8 +80,8 @@ export async function collectTests(ctx: Vitest, filepath: string): Promise<null
const { arguments: [{ value: message }] } = node as any
const property = callee?.property?.name
const mode = !property || property === name ? 'run' : property
if (mode === 'each')
throw new Error(`${name}.each syntax is not supported when testing types`)
if (!['run', 'skip', 'todo', 'only'].includes(mode))
throw new Error(`${name}.${mode} syntax is not supported when testing types`)
definitions.push({
start: node.start,
end: node.end,
Expand Down
10 changes: 8 additions & 2 deletions packages/vitest/src/typescript/typechecker.ts
Expand Up @@ -172,10 +172,16 @@ export class Typechecker {
this.process?.kill()
}

protected async ensurePackageInstalled(root: string, checker: string) {
if (checker !== 'tsc' && checker !== 'vue-tsc')
return
const packageName = checker === 'tsc' ? 'typescript' : 'vue-tsc'
await ensurePackageInstalled(packageName, root)
}

public async start() {
const { root, watch, typecheck } = this.ctx.config
const packageName = typecheck.checker === 'tsc' ? 'typescript' : 'vue-tsc'
await ensurePackageInstalled(packageName, root)
await this.ensurePackageInstalled(root, typecheck.checker)

this.tmpConfigPath = await getTsconfigPath(root, typecheck)
let cmd = `${typecheck.checker} --noEmit --pretty false -p ${this.tmpConfigPath}`
Expand Down

0 comments on commit ffd1377

Please sign in to comment.