Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 6 additions & 7 deletions api/advanced/plugin.md
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,6 @@ vitest.config.project.push('my-project-name')
请注意,这也将继承 `name` - Vitest 不允许多个项目使用相同的名称,因此这将引发错误。请确保我们指定了不同的名称。我们可以通过 `project.name` 属性访问当前名称,并且所有使用的名称都可以在 `vitest.projects` 数组中找到。
:::

<!-- TODO: translation -->
### experimental_defineCacheKeyGenerator <Version type="experimental">4.0.11</Version> <Experimental /> {#definecachekeygenerator}

```ts
Expand All @@ -139,11 +138,11 @@ function experimental_defineCacheKeyGenerator(
): void
```

Define a generator that will be applied before hashing the cache key.
定义一个生成器,它将在哈希缓存键之前应用。

Use this to make sure Vitest generates correct hash. It is a good idea to define this function if your plugin can be registered with different options.
使用此方法确保 Vitest 生成正确的哈希。如果你的插件可以使用不同的选项注册,定义此函数是一个好主意。

This is called only if [`experimental.fsModuleCache`](/config/experimental#experimental-fsmodulecache) is defined.
仅当定义了 [`experimental.fsModuleCache`](/config/experimental#experimental-fsmodulecache) 时才会调用此方法。

```ts
interface PluginOptions {
Expand All @@ -162,13 +161,13 @@ export function plugin(options: PluginOptions) {
},
configureVitest({ experimental_defineCacheKeyGenerator }) {
experimental_defineCacheKeyGenerator(() => {
// since these options affect the transform result,
// return them together as a unique string
// 由于这些选项会影响转换结果,
// 将它们作为唯一字符串一起返回
return options.replacePropertyKey + options.replacePropertyValue
})
}
}
}
```

If `false` is returned, the module will not be cached on the file system.
如果返回 `false`,模块将不会缓存在文件系统上。
7 changes: 3 additions & 4 deletions api/advanced/reporters.md
Original file line number Diff line number Diff line change
Expand Up @@ -330,7 +330,6 @@ onTestAnnotate 是与 [`context.annotate`](/guide/test-context#annotate) 方法

如果在注解中指定了文件路径, Vitest 会将附件保存到一个独立的目录(该目录通过 [`attachmentsDir`](/config/#attachmentsdir) 配置),并自动更新 path 属性,使其指向存储后的文件位置。

<!-- TODO: translation -->
## onTestCaseArtifactRecord <Version type="experimental">4.0.11</Version> {#ontestcaseartifactrecord}

```ts
Expand All @@ -340,8 +339,8 @@ function onTestCaseArtifactRecord(
): Awaitable<void>
```

The `onTestCaseArtifactRecord` hook is associated with the [`recordArtifact`](/api/advanced/artifacts#recordartifact) utility. When `recordArtifact` is invoked, Vitest serialises it and sends the same attachment to the main thread where reporter can interact with it.
`onTestCaseArtifactRecord` 钩子与 [`recordArtifact`](/api/advanced/artifacts#recordartifact) 工具相关联。当调用 `recordArtifact` 时,Vitest 会将其序列化并将相同的附件发送到主线程,报告器可以在那里与其交互。

If the path is specified, Vitest stores it in a separate directory (configured by [`attachmentsDir`](/config/#attachmentsdir)) and modifies the `path` property to reference it.
如果指定了路径,Vitest 会将其存储在单独的目录中(由 [`attachmentsDir`](/config/#attachmentsdir) 配置),并修改 `path` 属性以引用它。

Note: annotations, [even though they're built on top of this feature](/api/advanced/artifacts#relationship-with-annotations), won't hit this hook and won't appear in the `task.artifacts` array for backwards compatibility reasons until the next major version.
注意:注解,[即使它们是基于此功能构建的](/api/advanced/artifacts#relationship-with-annotations),出于向后兼容性原因,在下一个主要版本之前不会触发此钩子,也不会出现在 `task.artifacts` 数组中。
6 changes: 3 additions & 3 deletions api/advanced/test-case.md
Original file line number Diff line number Diff line change
Expand Up @@ -265,19 +265,19 @@ interface TestDiagnostic {
::: info
如果测试尚未被安排运行,`diagnostic()` 将返回 `undefined`。
:::
<!-- TODO: translation -->

## annotations

```ts
function annotations(): ReadonlyArray<TestAnnotation>
```

[Test annotations](/guide/test-annotations) added via the [`task.annotate`](/guide/test-context#annotate) API during the test execution.
在测试执行期间通过 [`task.annotate`](/guide/test-context#annotate) API 添加的[测试注释](/guide/test-annotations)。

## artifacts <Version type="experimental">4.0.11</Version> <Experimental /> {#artifacts}

```ts
function artifacts(): ReadonlyArray<TestArtifact>
```

[Test artifacts](/api/advanced/artifacts) recorded via the `recordArtifact` API during the test execution.
在测试执行期间通过 `recordArtifact` API 记录的[测试工件](/api/advanced/artifacts)
14 changes: 7 additions & 7 deletions api/advanced/test-suite.md
Original file line number Diff line number Diff line change
Expand Up @@ -63,13 +63,13 @@ ID 的格式如下:

::: tip
你可以使用 `vitest/node` 中的 `generateFileHash` 函数生成文件哈希,该函数自 Vitest 3 起可用:
<!-- TODO: translation -->

```ts
import { generateFileHash } from 'vitest/node'

const hash = generateFileHash(
'/file/path.js', // relative path
undefined // the project name or `undefined` is not set
'/file/path.js', // 相对路径
undefined // 项目名称,如果未设置则为 `undefined`
)
```

Expand Down Expand Up @@ -199,19 +199,19 @@ describe('collection failed', () => {
function meta(): TaskMeta
```
在执行或收集过程中附加到套件的自定义[元数据](/api/advanced/metadata)。在测试运行期间,可以通过向 `task.meta` 对象分配属性来附加 meta:
<!-- TODO: translation -->

```ts {7,12}
import { test } from 'vitest'
import { getCurrentSuite } from 'vitest/suite'

describe('the validation works correctly', () => {
// assign "decorated" during collection
// 在收集期间分配 "decorated"
const { suite } = getCurrentSuite()
suite!.meta.decorated = true

test('some test', ({ task }) => {
// 在试运行期间指定 “decorated,它将可用
// 仅在 onTestCaseReady hook
// 在测试运行期间分配 "decorated",它将可用
// 仅在 onTestCaseReady hook
task.suite.meta.decorated = false
})
})
Expand Down
16 changes: 8 additions & 8 deletions api/advanced/vitest.md
Original file line number Diff line number Diff line change
Expand Up @@ -463,8 +463,8 @@ function onCancel(fn: (reason: CancelReason) => Awaitable<void>): () => void

注册一个处理程序,当测试运行被 [`vitest.cancelCurrentRun`](#cancelcurrentrun) 取消时调用。

::: warning EXPERIMENTAL
Since 4.0.10, `onCancel` returns a teardown function that will remove the listener.
::: warning 实验性
4.0.10 起,`onCancel` 返回一个清理函数,用于移除监听器。
:::

## onClose
Expand Down Expand Up @@ -611,16 +611,16 @@ function experimental_parseSpecifications(
}
): Promise<TestModule[]>
```
<!-- TODO: translation -->
This method will [collect tests](#parsespecification) from an array of specifications. By default, Vitest will run only `os.availableParallelism()` number of specifications at a time to reduce the potential performance degradation. You can specify a different number in a second argument.

此方法将从规范数组中 [收集测试](#parsespecification)。默认情况下,Vitest 一次只运行 `os.availableParallelism()` 数量的规范,以减少潜在的性能下降。你可以在第二个参数中指定不同的数字。

## experimental_clearCache <Version type="experimental">4.0.11</Version> <Experimental /> {#clearcache}

```ts
function experimental_clearCache(): Promise<void>
```

Deletes all Vitest caches, including [`experimental.fsModuleCache`](/config/experimental#experimental-fsmodulecache).
删除所有 Vitest 缓存,包括 [`experimental.fsModuleCache`](/config/experimental#experimental-fsmodulecache)

## experimental_getSourceModuleDiagnostic <Version type="experimental">4.0.15</Version> <Experimental /> {#getsourcemodulediagnostic}

Expand All @@ -631,7 +631,7 @@ export function experimental_getSourceModuleDiagnostic(
): Promise<SourceModuleDiagnostic>
```

::: details Types
::: details 类型
```ts
export interface ModuleDefinitionLocation {
line: number
Expand Down Expand Up @@ -673,8 +673,8 @@ export interface SourceModuleDiagnostic {
```
:::

Returns module's diagnostic. If [`testModule`](/api/advanced/test-module) is not provided, `selfTime` and `totalTime` will be aggregated across all tests that were running the last time. If the module was not transformed or executed, the diagnostic will be empty.
返回模块的诊断信息。如果未提供 [`testModule`](/api/advanced/test-module)`selfTime` `totalTime` 将汇总上次运行的所有测试。如果模块未被转换或执行,诊断信息将为空。

::: warning
At the moment, the [browser](/guide/browser/) modules are not supported.
目前不支持 [浏览器](/guide/browser/) 模块。
:::
22 changes: 11 additions & 11 deletions api/browser/interactivity.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,28 +61,28 @@ test('clicks on an element', async () => {
// 或者你可以直接从定位器上访问
await logo.click()
// With WebdriverIO, this uses either ElementClick (with no arguments) or
// actions (with arguments). Use an empty object to force the use of actions.
// 使用 WebdriverIO 时,这会使用 ElementClick(无参数时)或
// actions(有参数时)。使用空对象可以强制使用 actions
await logo.click({})
})
```
<!-- TODO: translation -->
### Clicking with a modifier

With either WebdriverIO or Playwright:
### 使用修饰键点击

使用 WebdriverIOPlaywright

```ts
await userEvent.keyboard('{Shift>}')
// By using an empty object as the option, this opts in to using a chain of actions
// instead of an ElementClick in webdriver.
// Firefox has a bug that makes this necessary.
// Follow https://bugzilla.mozilla.org/show_bug.cgi?id=1456642 to know when this
// will be fixed.
// 通过使用空对象作为选项,这会选择使用一系列操作
// 而不是 webdriver 中的 ElementClick
// Firefox 有一个 bug 使这成为必要。
// 关注 https://bugzilla.mozilla.org/show_bug.cgi?id=1456642 以了解何时
// 修复此问题。
await userEvent.click(element, {})
await userEvent.keyboard('{/Shift}')
```

With Playwright:
使用 Playwright
```ts
await userEvent.click(element, { modifiers: ['Shift'] })
```
Expand Down
21 changes: 10 additions & 11 deletions api/browser/locators.md
Original file line number Diff line number Diff line change
Expand Up @@ -245,18 +245,18 @@ function getByLabelText(
<label id="username-label">Username</label>
<input aria-labelledby="username-label" />

// Wrapper labels
// 包裹式标签
<label>Username <input /></label>

// Wrapper labels where the label text is in another child element
// 标签文本在另一个子元素中的包裹式标签
<label>
<span>Username</span>
<input />
</label>

// aria-label attributes
// Take care because this is not a label that users can see on the page,
// so the purpose of your input must be obvious to visual users.
// aria-label 属性
// 请注意,这不是用户在页面上能看到的标签,
// 因此输入框的用途必须对视觉用户来说是显而易见的。
<input aria-label="Username" />
```

Expand Down Expand Up @@ -784,7 +784,7 @@ function screenshot(options?: LocatorScreenshotOptions & { base64?: false }): Pr
你可以使用 `path` 选项指定屏幕截图的保存位置,该选项相对于当前测试文件。如果未设置 `path` 选项,Vitest 将默认使用 [`browser.screenshotDirectory`](/config/browser/screenshotdirectory)(默认为 `__screenshot__`),并结合文件名和测试名来确定屏幕截图的文件路径。

如果你还需要屏幕截图的内容,可以指定 `base64: true` 以返回屏幕截图的 base64 编码内容以及保存路径。
<!-- TODO: translation -->

```ts
import { page } from 'vitest/browser'

Expand All @@ -794,10 +794,10 @@ const path = await button.screenshot()

const { path, base64 } = await button.screenshot({
path: './button-click-me.png',
base64: true, // also return base64 string
base64: true, // 同时返回 base64 字符串
})
// path - fullpath to the screenshot
// bas64 - base64 encoded string of the screenshot
// path - 屏幕截图的完整路径
// base64 - 屏幕截图的 base64 编码字符串
```

::: warning WARNING <Version>3.2.0</Version>
Expand Down Expand Up @@ -959,8 +959,7 @@ test('works correctly', async () => {

### length

This getter returns a number of elements that this locator is matching. It is equivalent to calling `locator.elements().length`.
此属性返回当前定位器匹配的元素数量,等效于调用 g `locator.elements().length`。
此属性返回当前定位器匹配的元素数量,等效于调用 `locator.elements().length`。

参考以下 DOM 结构:

Expand Down
11 changes: 5 additions & 6 deletions api/expect-typeof.md
Original file line number Diff line number Diff line change
Expand Up @@ -553,23 +553,22 @@ expectTypeOf(obj).toHaveProperty('b').toBeString()
expectTypeOf(obj).toHaveProperty('a').not.toBeString()
```

<!-- TODO: translation -->
## branded

- **Type:** `ExpectTypeOf<BrandedType>`
- **类型:** `ExpectTypeOf<BrandedType>`

You can use `.branded` to allow type assertions to succeed for types that are semantically equivalent but differ in representation.
你可以使用 `.branded` 来允许类型断言对语义上等效但表示形式不同的类型成功。

```ts
import { expectTypeOf } from 'vitest'

// Without .branded, this fails even though the types are effectively the same
// 没有 .branded,即使类型实际上相同,这也会失败
expectTypeOf<{ a: { b: 1 } & { c: 1 } }>().toEqualTypeOf<{ a: { b: 1; c: 1 } }>()

// With .branded, the assertion succeeds
// 使用 .branded,断言成功
expectTypeOf<{ a: { b: 1 } & { c: 1 } }>().branded.toEqualTypeOf<{ a: { b: 1; c: 1 } }>()
```

::: warning
This helper comes at a performance cost and can cause the TypeScript compiler to 'give up' if used with excessively deep types. Use it sparingly and only when necessary.
此辅助函数会带来性能成本,如果用于过深的类型,可能会导致 TypeScript 编译器"放弃"。请谨慎使用,仅在必要时使用。
:::
29 changes: 14 additions & 15 deletions api/expect.md
Original file line number Diff line number Diff line change
Expand Up @@ -189,8 +189,7 @@ test('stocks are the same', () => {

- **类型:** `(value: number, numDigits?: number) => Awaitable<void>`

<!-- TODO: translation -->
Use `toBeCloseTo` to compare floating-point numbers. The optional `numDigits` argument limits the number of digits to check _after_ the decimal point. The default for `numDigits` is 2. For example:
使用 `toBeCloseTo` 来比较浮点数。可选的 `numDigits` 参数用于限制小数点_后_要检查的位数。`numDigits` 的默认值为 2。例如:

```ts
import { expect, test } from 'vitest'
Expand Down Expand Up @@ -380,13 +379,13 @@ test('getApplesCount has some unusual side effects...', () => {
```

## toBeOneOf
<!-- TODO: translation -->
- **Type:** `(sample: Array<any> | Set<any>) => any`

`toBeOneOf` asserts if a value matches any of the values in the provided array or set.
- **类型:** `(sample: Array<any> | Set<any>) => any`

::: warning EXPERIMENTAL
Providing a `Set` is an experimental feature and may change in a future release.
`toBeOneOf` 断言一个值是否匹配提供的数组或集合中的任意一个值。

::: warning 实验性功能
提供 `Set` 是一个实验性功能,可能会在未来版本中发生变化。
:::

```ts
Expand Down Expand Up @@ -648,7 +647,7 @@ test('toHaveLength', () => {
expect('abc').toHaveLength(3)
expect([1, 2, 3]).toHaveLength(3)

expect('').not.toHaveLength(3) // doesn't have .length of 3
expect('').not.toHaveLength(3) // 长度不为 3
expect({ length: 3 }).toHaveLength(3)
})
```
Expand Down Expand Up @@ -707,7 +706,7 @@ test('John Doe Invoice', () => {
// 将键名包裹在数组中,避免其被解析为深层引用
expect(invoice).toHaveProperty(['P.O'], '12345')

// Deep equality of object property
// 对象属性的深度相等
expect(invoice).toHaveProperty('items[0]', { type: 'apples', quantity: 10 })
})
```
Expand All @@ -723,7 +722,7 @@ import { expect, test } from 'vitest'

test('top fruits', () => {
expect('top fruits include apple, orange and grape').toMatch(/apple/)
expect('applefruits').toMatch('fruit') // toMatch also accepts a string
expect('applefruits').toMatch('fruit') // toMatch 也接受字符串
})
```

Expand Down Expand Up @@ -770,8 +769,8 @@ test('invoice has john personal details', () => {
expect(johnInvoice).toMatchObject(johnDetails)
})

test('the number of elements must match exactly', () => {
// Assert that an array of object matches
test('元素数量必须完全匹配', () => {
// 断言对象数组匹配
expect([{ foo: 'bar' }, { baz: 1 }]).toMatchObject([
{ foo: 'bar' },
{ baz: 1 },
Expand Down Expand Up @@ -1234,7 +1233,7 @@ test('spy function returns bananas on a last call', () => {

我们可以调用这个断言来检查函数是否在特定的调用中成功返回了带有特定参数的值。需要将一个 spy 函数传递给 `expect`。

The count starts at 1. So, to check the second entry, you would write `.toHaveNthReturnedWith(2, ...)`.
计数从 1 开始。因此,要检查第二个条目,你需要写 `.toHaveNthReturnedWith(2, ...)`

```ts
import { expect, test, vi } from 'vitest'
Expand Down Expand Up @@ -1713,9 +1712,9 @@ test('variety ends with "re"', () => {

## expect.schemaMatching

- **Type:** `(expected: StandardSchemaV1) => any`
- **类型:** `(expected: StandardSchemaV1) => any`

When used with an equality check, this asymmetric matcher will return `true` if the value matches the provided schema. The schema must implement the [Standard Schema v1](https://standardschema.dev/) specification.
当与相等性检查一起使用时,如果值与提供的 schema 匹配,此非对称匹配器将返回 `true`schema 必须实现 [Standard Schema v1](https://standardschema.dev/) 规范。

```ts
import { expect, test } from 'vitest'
Expand Down
Loading