vitest-plugin-vis 3.1.0 → 3.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,471 @@
1
+ import { Meta } from "@storybook/addon-docs/blocks";
2
+
3
+ <Meta title="page/toMatchImageSnapshot" />
4
+
5
+ # page.toMatchImageSnapshot
6
+
7
+ `page.toMatchImageSnapshot()` is a method that captures and compares full page or viewport screenshots against baseline images.
8
+
9
+ Unlike `expect().toMatchImageSnapshot()` which targets specific elements, `page.toMatchImageSnapshot()` is designed for capturing entire pages or viewports, making it ideal for full-page visual regression testing.
10
+
11
+ ## Basic Usage
12
+
13
+ ```ts
14
+ import { page } from '@vitest/browser/context'
15
+
16
+ it('should take a page snapshot', async () => {
17
+ // Your test setup here
18
+ render(<MyApp />)
19
+
20
+ // Take a viewport snapshot
21
+ await page.toMatchImageSnapshot()
22
+ })
23
+ ```
24
+
25
+ ## Options
26
+
27
+ The `page.toMatchImageSnapshot()` method accepts an optional options object with the following properties:
28
+
29
+ ### Page Capture Options
30
+
31
+ #### `fullPage`
32
+
33
+ Capture the entire page including content below the fold, not just the visible viewport.
34
+
35
+ ```ts
36
+ it('should capture full page', async () => {
37
+ render(<LongPageContent />)
38
+
39
+ // Capture the entire scrollable page
40
+ await page.toMatchImageSnapshot({
41
+ fullPage: true
42
+ })
43
+ })
44
+
45
+ it('should capture viewport only', async () => {
46
+ render(<LongPageContent />)
47
+
48
+ // Capture only the visible viewport (default)
49
+ await page.toMatchImageSnapshot({
50
+ fullPage: false // default
51
+ })
52
+ })
53
+ ```
54
+
55
+ ### Snapshot Identification
56
+
57
+ #### `snapshotKey`
58
+
59
+ Customize the snapshot key/name for the snapshot file.
60
+
61
+ ```ts
62
+ it('should use custom snapshot key', async () => {
63
+ render(<MyApp />)
64
+
65
+ await page.toMatchImageSnapshot({
66
+ snapshotKey: 'homepage_layout'
67
+ })
68
+ })
69
+ ```
70
+
71
+ ### Failure Threshold
72
+
73
+ #### `failureThreshold` and `failureThresholdType`
74
+
75
+ Control how much difference is allowed before the test fails.
76
+
77
+ ```ts
78
+ // Allow up to 100 pixels to be different
79
+ it('should allow pixel differences', async () => {
80
+ render(<MyApp />)
81
+
82
+ await page.toMatchImageSnapshot({
83
+ failureThreshold: 100,
84
+ failureThresholdType: 'pixel' // default
85
+ })
86
+ })
87
+
88
+ // Allow up to 0.5% difference
89
+ it('should allow percentage differences', async () => {
90
+ render(<MyApp />)
91
+
92
+ await page.toMatchImageSnapshot({
93
+ failureThreshold: 0.005,
94
+ failureThresholdType: 'percent'
95
+ })
96
+ })
97
+ ```
98
+
99
+ ### Comparison Methods
100
+
101
+ #### `comparisonMethod`
102
+
103
+ Choose between pixel-by-pixel comparison or structural similarity comparison.
104
+
105
+ ```ts
106
+ // Default pixel comparison
107
+ it('should use pixel comparison', async () => {
108
+ render(<MyApp />)
109
+
110
+ await page.toMatchImageSnapshot({
111
+ comparisonMethod: 'pixel' // default
112
+ })
113
+ })
114
+
115
+ // SSIM (Structural Similarity) comparison
116
+ it('should use SSIM comparison', async () => {
117
+ render(<MyApp />)
118
+
119
+ await page.toMatchImageSnapshot({
120
+ comparisonMethod: 'ssim'
121
+ })
122
+ })
123
+ ```
124
+
125
+ ### Diff Options
126
+
127
+ #### `diffOptions` for Pixel Comparison
128
+
129
+ When using `comparisonMethod: 'pixel'` (default), you can customize pixelmatch options:
130
+
131
+ ```ts
132
+ it('should use custom pixel diff options', async () => {
133
+ render(<MyApp />)
134
+
135
+ await page.toMatchImageSnapshot({
136
+ comparisonMethod: 'pixel',
137
+ diffOptions: {
138
+ threshold: 0.1, // Matching threshold (0-1, default: 0.1)
139
+ includeAA: false, // Include anti-aliased pixels (default: false)
140
+ alpha: 0.1, // Blending factor for unchanged pixels (default: 0.1)
141
+ aaColor: [255, 255, 0], // Color for anti-aliased pixels [R, G, B]
142
+ diffColor: [255, 0, 0], // Color for different pixels [R, G, B]
143
+ diffColorAlt: null, // Alternative color for dark-on-light differences
144
+ diffMask: false // Draw diff over transparent background (default: false)
145
+ }
146
+ })
147
+ })
148
+ ```
149
+
150
+ #### `diffOptions` for SSIM Comparison
151
+
152
+ When using `comparisonMethod: 'ssim'`, you can customize SSIM options:
153
+
154
+ ```ts
155
+ it('should use custom SSIM diff options', async () => {
156
+ render(<MyApp />)
157
+
158
+ await page.toMatchImageSnapshot({
159
+ comparisonMethod: 'ssim',
160
+ diffOptions: {
161
+ ssim: 'bezkrovny', // 'bezkrovny' (fast, default) | 'fast' (accurate) | 'weber' | 'original'
162
+ windowSize: 11, // Window size for SSIM calculation (default: 11)
163
+ k1: 0.01, // First stability constant (default: 0.01)
164
+ k2: 0.03, // Second stability constant (default: 0.03)
165
+ bitDepth: 8, // Bits per channel (default: 8)
166
+ downsample: 'original' // 'original' | 'fast' | false
167
+ }
168
+ })
169
+ })
170
+ ```
171
+
172
+ ### Timeout
173
+
174
+ #### `timeout`
175
+
176
+ Set a timeout for taking the snapshot.
177
+
178
+ ```ts
179
+ it('should use custom timeout', async () => {
180
+ render(<MyApp />)
181
+
182
+ await page.toMatchImageSnapshot({
183
+ timeout: 60000 // 60 seconds (default: 30000ms)
184
+ })
185
+ })
186
+ ```
187
+
188
+ ### Testing Utilities
189
+
190
+ #### `expectToFail`
191
+
192
+ Expect the matcher to fail - useful for testing that changes are detected.
193
+
194
+ ```ts
195
+ it('should detect page differences', async () => {
196
+ render(<MyApp />)
197
+
198
+ // First, create the baseline
199
+ if (!(await page.hasImageSnapshot({ snapshotKey: 'page_changes' }))) {
200
+ await page.toMatchImageSnapshot({
201
+ snapshotKey: 'page_changes'
202
+ })
203
+ return
204
+ }
205
+
206
+ // Modify the page
207
+ document.body.style.backgroundColor = 'red'
208
+
209
+ // Expect the test to fail due to changes
210
+ await page.toMatchImageSnapshot({
211
+ snapshotKey: 'page_changes',
212
+ expectToFail: true
213
+ })
214
+ .then(
215
+ () => {
216
+ throw new Error('Should not reach - expected failure')
217
+ },
218
+ (error) => {
219
+ expect(error.message).toMatch(/Expected image to match but was differ by \d+ pixels/)
220
+ }
221
+ )
222
+ })
223
+ ```
224
+
225
+ ## Complete Example
226
+
227
+ Here's a comprehensive example showing multiple options:
228
+
229
+ ```ts
230
+ it('should demonstrate all page snapshot options', async () => {
231
+ render(<MyComplexApp />)
232
+
233
+ await page.toMatchImageSnapshot({
234
+ // Page capture
235
+ fullPage: true,
236
+
237
+ // Snapshot identification
238
+ snapshotKey: 'full_app_layout',
239
+
240
+ // Failure threshold
241
+ failureThreshold: 0.01,
242
+ failureThresholdType: 'percent',
243
+
244
+ // Comparison method
245
+ comparisonMethod: 'ssim',
246
+
247
+ // SSIM-specific options
248
+ diffOptions: {
249
+ ssim: 'bezkrovny',
250
+ windowSize: 11,
251
+ k1: 0.01,
252
+ k2: 0.03
253
+ },
254
+
255
+ // Timeout
256
+ timeout: 45000,
257
+
258
+ // Testing utility
259
+ expectToFail: false
260
+ })
261
+ })
262
+ ```
263
+
264
+ ## Use Cases
265
+
266
+ ### Full Page Layout Testing
267
+
268
+ Perfect for testing complete page layouts, including content below the fold:
269
+
270
+ ```ts
271
+ it('should capture entire homepage layout', async () => {
272
+ render(<Homepage />)
273
+
274
+ await page.toMatchImageSnapshot({
275
+ fullPage: true,
276
+ snapshotKey: 'homepage_complete',
277
+ failureThreshold: 0.01,
278
+ failureThresholdType: 'percent'
279
+ })
280
+ })
281
+ ```
282
+
283
+ ### Viewport Testing
284
+
285
+ Test how your application appears in the current viewport:
286
+
287
+ ```ts
288
+ it('should capture above-the-fold content', async () => {
289
+ render(<LandingPage />)
290
+
291
+ await page.toMatchImageSnapshot({
292
+ fullPage: false, // default - viewport only
293
+ snapshotKey: 'landing_viewport'
294
+ })
295
+ })
296
+ ```
297
+
298
+ ### Responsive Design Testing
299
+
300
+ Test different viewport sizes by combining with browser configuration:
301
+
302
+ ```ts
303
+ it('should test mobile layout', async () => {
304
+ // Assuming viewport is configured for mobile in test setup
305
+ render(<ResponsiveApp />)
306
+
307
+ await page.toMatchImageSnapshot({
308
+ snapshotKey: 'mobile_layout',
309
+ fullPage: true
310
+ })
311
+ })
312
+ ```
313
+
314
+ ### Cross-Browser Consistency
315
+
316
+ Ensure consistent rendering across different browsers:
317
+
318
+ ```ts
319
+ it('should render consistently across browsers', async () => {
320
+ render(<CrossBrowserApp />)
321
+
322
+ await page.toMatchImageSnapshot({
323
+ snapshotKey: 'cross_browser_test',
324
+ comparisonMethod: 'ssim', // More forgiving for browser differences
325
+ failureThreshold: 0.02,
326
+ failureThresholdType: 'percent'
327
+ })
328
+ })
329
+ ```
330
+
331
+ ## Comparison Method Recommendations
332
+
333
+ ### When to use Pixel Comparison (`comparisonMethod: 'pixel'`)
334
+
335
+ - **Default choice** for most page-level visual regression tests
336
+ - **Precise detection** of layout shifts, color changes, and text modifications
337
+ - **Good for** detecting critical visual regressions
338
+ - **Fast execution** for most page sizes
339
+
340
+ ### When to use SSIM Comparison (`comparisonMethod: 'ssim'`)
341
+
342
+ - **Structural similarity** comparison that's more forgiving of minor rendering differences
343
+ - **Reduced false positives** from browser-specific rendering variations
344
+ - **Better for** pages with complex graphics, gradients, or anti-aliased content
345
+ - **Recommended for** cross-browser testing where minor pixel differences are expected
346
+
347
+ ```ts
348
+ // Recommended SSIM configuration for page testing
349
+ it('should use recommended SSIM settings for pages', async () => {
350
+ render(<MyApp />)
351
+
352
+ await page.toMatchImageSnapshot({
353
+ comparisonMethod: 'ssim',
354
+ failureThreshold: 0.01,
355
+ failureThresholdType: 'percent',
356
+ diffOptions: {
357
+ ssim: 'bezkrovny' // Fast and accurate for most cases
358
+ }
359
+ })
360
+ })
361
+ ```
362
+
363
+ ## Best Practices
364
+
365
+ ### 1. Use Descriptive Snapshot Keys
366
+
367
+ ```ts
368
+ // Good
369
+ await page.toMatchImageSnapshot({
370
+ snapshotKey: 'dashboard_with_data_loaded'
371
+ })
372
+
373
+ // Better
374
+ await page.toMatchImageSnapshot({
375
+ snapshotKey: 'user_dashboard_logged_in_state'
376
+ })
377
+ ```
378
+
379
+ ### 2. Consider Page Loading States
380
+
381
+ ```ts
382
+ it('should wait for page to be fully loaded', async () => {
383
+ render(<AsyncApp />)
384
+
385
+ // Wait for async content to load
386
+ await page.waitForSelector('[data-testid="content-loaded"]')
387
+
388
+ await page.toMatchImageSnapshot({
389
+ snapshotKey: 'fully_loaded_page'
390
+ })
391
+ })
392
+ ```
393
+
394
+ ### 3. Use Appropriate Failure Thresholds
395
+
396
+ ```ts
397
+ // For critical UI elements - strict comparison
398
+ await page.toMatchImageSnapshot({
399
+ snapshotKey: 'critical_layout',
400
+ failureThreshold: 0 // No differences allowed
401
+ })
402
+
403
+ // For pages with dynamic content - more lenient
404
+ await page.toMatchImageSnapshot({
405
+ snapshotKey: 'dynamic_content_page',
406
+ failureThreshold: 0.5,
407
+ failureThresholdType: 'percent'
408
+ })
409
+ ```
410
+
411
+ ### 4. Choose Full Page vs Viewport Strategically
412
+
413
+ ```ts
414
+ // Use fullPage for complete layout testing
415
+ await page.toMatchImageSnapshot({
416
+ fullPage: true,
417
+ snapshotKey: 'complete_article_layout'
418
+ })
419
+
420
+ // Use viewport for above-the-fold testing
421
+ await page.toMatchImageSnapshot({
422
+ fullPage: false,
423
+ snapshotKey: 'hero_section'
424
+ })
425
+ ```
426
+
427
+ ## Limitations
428
+
429
+ ### Concurrent Tests
430
+
431
+ `page.toMatchImageSnapshot()` cannot be used in concurrent tests as they share the same browser environment:
432
+
433
+ ```ts
434
+ // ❌ This will throw an error
435
+ it.concurrent('concurrent test', async () => {
436
+ await page.toMatchImageSnapshot() // Error: cannot be called in concurrent test
437
+ })
438
+
439
+ // ✅ Use regular tests instead
440
+ it('sequential test', async () => {
441
+ await page.toMatchImageSnapshot() // Works fine
442
+ })
443
+ ```
444
+
445
+ ### WebDriverIO Considerations
446
+
447
+ When using WebDriverIO as the browser provider:
448
+
449
+ - `fullPage` option may not work correctly in headless mode
450
+ - Consider setting explicit window size in configuration
451
+ - Playwright is recommended for more reliable visual testing
452
+
453
+ ```ts
454
+ // vitest.config.ts - WebDriverIO workaround
455
+ export default {
456
+ test: {
457
+ browser: {
458
+ instances: [
459
+ {
460
+ browser: 'chrome',
461
+ capabilities: {
462
+ 'goog:chromeOptions': {
463
+ args: ['--window-size=1280,720']
464
+ }
465
+ }
466
+ }
467
+ ]
468
+ }
469
+ }
470
+ }
471
+ ```
package/src/client-api.ts CHANGED
@@ -7,6 +7,7 @@ export * from './client/actions/match_page_image_snapshot_action.ts'
7
7
  export { setAutoSnapshotOptions, type MetaTask } from './client/auto_snapshot_options.ts'
8
8
  export * from './client/expect/expectation_result.ts'
9
9
  export type * from './client/expect/to_match_image_snapshot.types.ts'
10
+ export * from './client/setup/create_vis.ts'
10
11
  export * from './client/task_id.ts'
11
12
  export * from './shared/constants.ts'
12
13
  export type * from './shared/types.ts'
@@ -34,12 +34,14 @@ export type VisOptions<M extends ComparisonMethod = 'pixel'> = (M extends 'ssim'
34
34
  /**
35
35
  * Loads the `test.setupFiles` of the specified preset.
36
36
  *
37
- * Note: 'enable` is deprecated. Use `manual` for the same effect.
37
+ * Note:
38
+ * - 'enable` is deprecated. Use `manual` for the same effect.
39
+ * - 'none` is deprecated. Use `custom` for the same effect.
38
40
  *
39
41
  * @default 'auto'
40
42
  *
41
43
  */
42
- preset?: 'enable' | 'manual' | 'auto' | 'none' | undefined
44
+ preset?: 'enable' | 'manual' | 'auto' | 'custom' | 'none' | undefined
43
45
  /**
44
46
  * The snapshot folder relative to the root of the project.
45
47
  *
package/src/config/vis.ts CHANGED
@@ -23,7 +23,7 @@ export function vis<M extends ComparisonMethod = 'pixel'>(options: VisOptions<M>
23
23
  name: undefined as unknown as string,
24
24
  commands,
25
25
  },
26
- setupFiles: preset && preset !== 'none' ? [`vitest-plugin-vis/presets/${preset}`] : [],
26
+ setupFiles: preset && preset !== 'none' && preset !== 'custom' ? [`vitest-plugin-vis/presets/${preset}`] : [],
27
27
  },
28
28
  }
29
29
  },
@@ -0,0 +1,76 @@
1
+ import { Meta, Source } from "@storybook/addon-docs/blocks";
2
+
3
+ <Meta title="vitest-plugin-vis/config/vis" />
4
+
5
+ `vis` from `vitest-plugin-vis/config` is the Vitest plugin of `vitest-plugin-vis`.
6
+
7
+ ```ts
8
+ // vitest.config.ts
9
+ import { vis } from 'vitest-plugin-vis/config'
10
+
11
+ export default defineConfig({
12
+ plugins: [vis()],
13
+ })
14
+ ```
15
+
16
+ It provides a lot of options to customize the behavior of the plugin.
17
+ (You can learn more about the default configuration [here](/docs/overview--docs#basic-configuration).)
18
+
19
+ ## Preset
20
+
21
+ The `preset` option set up typical visual testing strategies.
22
+
23
+ ### `auto`
24
+
25
+ The `auto` preset is the default preset.
26
+ It will take a snapshot of the page at the end of each rendering test.
27
+
28
+ ```ts
29
+ // vitest.config.ts
30
+ import { vis } from 'vitest-plugin-vis/config'
31
+
32
+ export default defineConfig({
33
+ plugins: [vis({ preset: 'auto' })],
34
+ })
35
+ ```
36
+
37
+ ### `manual`
38
+
39
+ The `manual` preset is for manual testing.
40
+ It will not take any snapshot automatically.
41
+
42
+ ```ts
43
+ // vitest.config.ts
44
+ import { vis } from 'vitest-plugin-vis/config'
45
+
46
+ export default defineConfig({
47
+ plugins: [vis({ preset: 'manual' })],
48
+ })
49
+ ```
50
+
51
+ See [Manual Snapshot](/docs/expect-tomatchimagesnapshot--docs) section on how to take an image snapshot manually.
52
+
53
+ ### `custom`
54
+
55
+ The `custom` preset is for advanced users.
56
+ It will not take any snapshot automatically.
57
+ You need to set up your own visual testing strategy in `vitest.setup.ts`.
58
+
59
+ ```ts
60
+ // vitest.config.ts
61
+ import { vis } from 'vitest-plugin-vis/config'
62
+
63
+ export default defineConfig({
64
+ plugins: [vis({ preset: 'custom' })],
65
+ test: {
66
+ // Set up your own visual testing strategy in `vitest.setup.ts`.
67
+ setupFiles: ['./vitest.setup.ts'],
68
+ }
69
+ })
70
+ ```
71
+
72
+ When using the `custom` preset, you can set up your own visual testing strategy in `vitest.setup.ts` using the [vis](/docs/vitest-plugin-vis-setup-vis--docs) object from `vitest-plugin-vis/setup`.
73
+
74
+ [vitest-plugin-vis]: https://npmjs.org/package/vitest-plugin-vis
75
+
76
+
@@ -0,0 +1,92 @@
1
+ import { Meta, Markdown } from "@storybook/addon-docs/blocks";
2
+
3
+ <Meta title="Overview" />
4
+
5
+ # Vitest Visual Testing Plugin
6
+
7
+ [vitest-plugin-vis] provides visual testing for [Vitest] when running in [Browser Mode][browser-mode].
8
+
9
+ It offers a new unique features:
10
+
11
+ - You can capture and compare image snapshot both automatically and manually.
12
+ - You can take a snapshot of the whole page or a specific component.
13
+ - You can take snapshots in different environments, platform, browser, screen size and themes.
14
+ - The snapshots are stored locally in the `__vis__` directory.
15
+ - You can enable, disable, and customize how the snapshots are taken and compared.
16
+
17
+ ## Install
18
+
19
+ [vitest-plugin-vis] works with Vitest 2.0.0 or later.
20
+
21
+ ```sh
22
+ npm install --save-dev vitest-plugin-vis
23
+
24
+ pnpm add --save-dev vitest-plugin-vis
25
+
26
+ yarn add --save-dev vitest-plugin-vis
27
+ ```
28
+
29
+ ## Basic Configuration
30
+
31
+ To use [vitest-plugin-vis], you need to add it to your Vitest configuration.
32
+
33
+ ```ts
34
+ // vitest.config.ts
35
+ import { defineConfig } from 'vitest/config'
36
+ import { vis } from 'vitest-plugin-vis/config'
37
+
38
+ export default defineConfig({
39
+ plugins: [vis()],
40
+ test: {
41
+ // vitest v2
42
+ browser: {
43
+ enabled: true,
44
+ provider: 'playwright',
45
+ name: 'chromium',
46
+ },
47
+ // vitest v3
48
+ browser: {
49
+ enabled: true,
50
+ provider: 'playwright',
51
+ instances: [
52
+ { browser: 'chromium' }
53
+ ]
54
+ }
55
+ }
56
+ })
57
+ ```
58
+
59
+ This default configuration will:
60
+
61
+ - Use the `auto` preset, taking image snapshot at the end on each rendering test.
62
+ - Use `pixelmatch` as the image comparison method.
63
+ - Set config to compare image snapshot with a failure threshold of `0 pixels`.
64
+ - Timeout for image comparison is set to `30000 ms`.
65
+ - Save image snapshots in the `<project-root>/__vis__` directory.
66
+
67
+ ## Update .gitignore
68
+
69
+ By default, [vitest-plugin-vis] will save image snapshots in the `<project-root>/__vis__` directory.
70
+
71
+ Under this directory, you will find different set of snapshots for different environments:
72
+
73
+ - `local`: For snapshots taken locally.
74
+ - `<platform: ubuntu | darwin | win32>`: Fom snapshots taken in respective CI.
75
+
76
+ In each platform directory, there are 3 directories:
77
+
78
+ - `__baselines__`: The directory for the baseline snapshots. This should be committed to the repository (except for `local`).
79
+ - `__results__`: The directory for the current snapshots created when Vitest runs.
80
+ - `__diffs__`: The directory for the diffs between the current snapshot and the baseline snapshot.
81
+
82
+ Because of that, you should add the following lines to your `.gitignore` file:
83
+
84
+ ```gitignore
85
+ **/__vis__/local
86
+ **/__vis__/**/__diffs__
87
+ **/__vis__/**/__results__
88
+ ```
89
+
90
+ [browser-mode]: https://vitest.dev/guide/browser
91
+ [vitest]: https://vitest.dev
92
+ [vitest-plugin-vis]: https://npmjs.org/package/vitest-plugin-vis
@@ -19,7 +19,15 @@ export function resolveSnapshotRootDir(browserCommandContext: PartialBrowserComm
19
19
  })
20
20
  }
21
21
 
22
- function getSnapshotRootDir(snapshotRootDir: string) {
22
+ /**
23
+ * Gets the root directory for storing snapshots.
24
+ *
25
+ * @param snapshotRootDir - Base directory for snapshots. Defaults to `__vis__`.
26
+ * @returns The full snapshot root directory path, which includes a platform-specific subdirectory:
27
+ * - When running in CI: `<snapshotRootDir>/<platform>` (e.g. `__vis__/linux`)
28
+ * - When running locally: `<snapshotRootDir>/local`
29
+ */
30
+ export function getSnapshotRootDir(snapshotRootDir = SNAPSHOT_ROOT_DIR) {
23
31
  return `${snapshotRootDir}/${ci ? platform : 'local'}`
24
32
  }
25
33
 
@@ -1,2 +1,3 @@
1
+ export { getSnapshotRootDir } from './server/snapshot_path.ts'
1
2
  export * from './shared/constants.ts'
2
3
  export * from './shared/trim_common_folder.ts'
@@ -0,0 +1,12 @@
1
+ import { Meta, Markdown ,Canvas} from "@storybook/addon-docs/blocks";
2
+
3
+ <Meta
4
+ tags={['deprecated']}
5
+ title="vitest-plugin-vis/setup/createVis"
6
+ />
7
+
8
+ 🪦 Deprecated
9
+
10
+ `createVis` in `vitest-plugin-vis/setup` is deprecated.
11
+
12
+ It is moved to `/client-api`.