@testing-library/svelte 5.0.0 → 5.1.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.
package/README.md CHANGED
@@ -13,7 +13,7 @@
13
13
  <p>Simple and complete Svelte testing utilities that encourage good testing practices.</p>
14
14
 
15
15
  [**Read The Docs**](https://testing-library.com/docs/svelte-testing-library/intro) |
16
- [Edit the docs](https://github.com/alexkrolick/testing-library-docs)
16
+ [Edit the docs](https://github.com/testing-library/testing-library-docs)
17
17
 
18
18
  <!-- prettier-ignore-start -->
19
19
  [![Build Status][build-badge]][build]
@@ -80,19 +80,42 @@ This library has `peerDependencies` listings for `svelte >= 3`.
80
80
  You may also be interested in installing `@testing-library/jest-dom` so you can use
81
81
  [the custom jest matchers](https://github.com/testing-library/jest-dom).
82
82
 
83
+ ## Setup
84
+
85
+ We recommend using `@testing-library/svelte` with [Vitest][] as your test runner. To get started, add the `svelteTesting` plugin to your Vite or Vitest config.
86
+
87
+ ```diff
88
+ // vite.config.js
89
+ import { svelte } from '@sveltejs/vite-plugin-svelte'
90
+ + import { svelteTesting } from '@testing-library/svelte/vite'
91
+
92
+ export default defineConfig({
93
+ plugins: [
94
+ svelte(),
95
+ + svelteTesting(),
96
+ ]
97
+ });
98
+ ```
99
+
100
+ See the [setup docs][] for more detailed setup instructions, including for other test runners like Jest.
101
+
102
+ [vitest]: https://vitest.dev/
103
+ [setup docs]: https://testing-library.com/docs/svelte-testing-library/setup
104
+
83
105
  ### Svelte 5 support
84
106
 
85
107
  If you are riding the bleeding edge of Svelte 5, you'll need to either
86
- import from `@testing-library/svelte/svelte5` instead of `@testing-library/svelte`, or have your `vite.config.js` contains the following alias:
108
+ import from `@testing-library/svelte/svelte5` instead of `@testing-library/svelte`, or add an alias to your `vite.config.js`:
87
109
 
88
- ```
89
- export default defineConfig(({ }) => ({
110
+ ```js
111
+ export default defineConfig({
112
+ plugins: [svelte(), svelteTesting()],
90
113
  test: {
91
114
  alias: {
92
- '@testing-library/svelte': '@testing-library/svelte/svelte5'
93
- }
115
+ '@testing-library/svelte': '@testing-library/svelte/svelte5',
116
+ },
94
117
  },
95
- }))
118
+ })
96
119
  ```
97
120
 
98
121
  ## Docs
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@testing-library/svelte",
3
- "version": "5.0.0",
3
+ "version": "5.1.0",
4
4
  "description": "Simple and complete Svelte testing utilities that encourage good testing practices.",
5
5
  "main": "src/index.js",
6
6
  "exports": {
@@ -14,6 +14,10 @@
14
14
  },
15
15
  "./vitest": {
16
16
  "default": "./src/vitest.js"
17
+ },
18
+ "./vite": {
19
+ "types": "./types/vite.d.ts",
20
+ "default": "./src/vite.js"
17
21
  }
18
22
  },
19
23
  "type": "module",
@@ -43,8 +47,10 @@
43
47
  "e2e"
44
48
  ],
45
49
  "files": [
46
- "src/",
47
- "types/index.d.ts"
50
+ "src",
51
+ "types",
52
+ "!*.test-d.ts",
53
+ "!__tests__"
48
54
  ],
49
55
  "scripts": {
50
56
  "toc": "doctoc README.md",
@@ -68,7 +74,17 @@
68
74
  "contributors:generate": "all-contributors generate"
69
75
  },
70
76
  "peerDependencies": {
71
- "svelte": "^3 || ^4 || ^5"
77
+ "svelte": "^3 || ^4 || ^5",
78
+ "vite": "*",
79
+ "vitest": "*"
80
+ },
81
+ "peerDependenciesMeta": {
82
+ "vite": {
83
+ "optional": true
84
+ },
85
+ "vitest": {
86
+ "optional": true
87
+ }
72
88
  },
73
89
  "dependencies": {
74
90
  "@testing-library/dom": "^9.3.1"
@@ -1,2 +1 @@
1
1
  import '@testing-library/jest-dom/vitest'
2
- import '../vitest'
package/src/vite.js ADDED
@@ -0,0 +1,75 @@
1
+ import { dirname, join } from 'node:path'
2
+ import { fileURLToPath } from 'node:url'
3
+
4
+ /**
5
+ * Vite plugin to configure @testing-library/svelte.
6
+ *
7
+ * Ensures Svelte is imported correctly in tests
8
+ * and that the DOM is cleaned up after each test.
9
+ *
10
+ * @param {{resolveBrowser?: boolean, autoCleanup?: boolean}} options
11
+ * @returns {import('vite').Plugin}
12
+ */
13
+ export const svelteTesting = ({
14
+ resolveBrowser = true,
15
+ autoCleanup = true,
16
+ } = {}) => ({
17
+ name: 'vite-plugin-svelte-testing-library',
18
+ config: (config) => {
19
+ if (!process.env.VITEST) {
20
+ return
21
+ }
22
+
23
+ if (resolveBrowser) {
24
+ addBrowserCondition(config)
25
+ }
26
+
27
+ if (autoCleanup) {
28
+ addAutoCleanup(config)
29
+ }
30
+ },
31
+ })
32
+
33
+ /**
34
+ * Add `browser` to `resolve.conditions` before `node`.
35
+ *
36
+ * This ensures that Svelte's browser code is used in tests,
37
+ * rather than its SSR code.
38
+ *
39
+ * @param {import('vitest/config').UserConfig} config
40
+ */
41
+ const addBrowserCondition = (config) => {
42
+ const resolve = config.resolve ?? {}
43
+ const conditions = resolve.conditions ?? []
44
+ const nodeConditionIndex = conditions.indexOf('node')
45
+ const browserConditionIndex = conditions.indexOf('browser')
46
+
47
+ if (
48
+ nodeConditionIndex >= 0 &&
49
+ (nodeConditionIndex < browserConditionIndex || browserConditionIndex < 0)
50
+ ) {
51
+ conditions.splice(nodeConditionIndex, 0, 'browser')
52
+ }
53
+
54
+ resolve.conditions = conditions
55
+ config.resolve = resolve
56
+ }
57
+
58
+ /**
59
+ * Add auto-cleanup file to Vitest's setup files.
60
+ *
61
+ * @param {import('vitest/config').UserConfig} config
62
+ */
63
+ const addAutoCleanup = (config) => {
64
+ const test = config.test ?? {}
65
+ let setupFiles = test.setupFiles ?? []
66
+
67
+ if (typeof setupFiles === 'string') {
68
+ setupFiles = [setupFiles]
69
+ }
70
+
71
+ setupFiles.push(join(dirname(fileURLToPath(import.meta.url)), './vitest.js'))
72
+
73
+ test.setupFiles = setupFiles
74
+ config.test = test
75
+ }
@@ -0,0 +1,65 @@
1
+ import { expectTypeOf } from 'expect-type'
2
+ import type { ComponentProps, SvelteComponent } from 'svelte'
3
+ import { describe, test } from 'vitest'
4
+
5
+ import Simple from '../src/__tests__/fixtures/Simple.svelte'
6
+ import * as subject from './index.js'
7
+
8
+ describe('types', () => {
9
+ test('render is a function that accepts a Svelte component', () => {
10
+ subject.render(Simple, { name: 'Alice', count: 42 })
11
+ subject.render(Simple, { props: { name: 'Alice', count: 42 } })
12
+ })
13
+
14
+ test('rerender is a function that accepts partial props', async () => {
15
+ const { rerender } = subject.render(Simple, { name: 'Alice', count: 42 })
16
+
17
+ await rerender({ name: 'Bob' })
18
+ await rerender({ count: 0 })
19
+ })
20
+
21
+ test('invalid prop types are rejected', () => {
22
+ // @ts-expect-error: name should be a string
23
+ subject.render(Simple, { name: 42 })
24
+
25
+ // @ts-expect-error: name should be a string
26
+ subject.render(Simple, { props: { name: 42 } })
27
+ })
28
+
29
+ test('render result has container and component', () => {
30
+ const result = subject.render(Simple, { name: 'Alice', count: 42 })
31
+
32
+ expectTypeOf(result).toMatchTypeOf<{
33
+ container: HTMLElement
34
+ component: SvelteComponent<{ name: string }>
35
+ debug: (el?: HTMLElement) => void
36
+ rerender: (props: Partial<ComponentProps<Simple>>) => Promise<void>
37
+ unmount: () => void
38
+ }>()
39
+ })
40
+
41
+ test('render result has default queries', () => {
42
+ const result = subject.render(Simple, { name: 'Alice', count: 42 })
43
+
44
+ expectTypeOf(result.getByRole).parameters.toMatchTypeOf<
45
+ [role: subject.ByRoleMatcher, options?: subject.ByRoleOptions]
46
+ >()
47
+ })
48
+
49
+ test('render result can have custom queries', () => {
50
+ const [getByVibes] = subject.buildQueries(
51
+ (_container: HTMLElement, vibes: string) => {
52
+ throw new Error(`unimplemented ${vibes}`)
53
+ },
54
+ () => '',
55
+ () => ''
56
+ )
57
+ const result = subject.render(
58
+ Simple,
59
+ { name: 'Alice', count: 42 },
60
+ { queries: { getByVibes } }
61
+ )
62
+
63
+ expectTypeOf(result.getByVibes).parameters.toMatchTypeOf<[vibes: string]>()
64
+ })
65
+ })
@@ -0,0 +1,12 @@
1
+ import type { Plugin } from 'vite'
2
+
3
+ /**
4
+ * Vite plugin to configure @testing-library/svelte.
5
+ *
6
+ * Ensures Svelte is imported correctly in tests
7
+ * and that the DOM is cleaned up after each test.
8
+ */
9
+ export function svelteTesting(options?: {
10
+ resolveBrowser?: boolean
11
+ autoCleanup?: boolean
12
+ }): Plugin