vitest-plugin-vis 1.0.5 → 1.2.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.
Files changed (113) hide show
  1. package/esm/client/align_images.d.ts +2 -0
  2. package/esm/client/align_images.d.ts.map +1 -0
  3. package/esm/client/align_images.js +10 -0
  4. package/esm/client/expect/to_match_image_snapshot.d.ts.map +1 -1
  5. package/esm/client/expect/to_match_image_snapshot.js +2 -15
  6. package/esm/client/image_data.d.ts +3 -0
  7. package/esm/client/image_data.d.ts.map +1 -0
  8. package/esm/client/image_data.js +33 -0
  9. package/esm/client/image_resizer.d.ts +9 -0
  10. package/esm/client/image_resizer.d.ts.map +1 -0
  11. package/esm/client/image_resizer.js +49 -0
  12. package/esm/client/match_image_snapshot.d.ts +8 -0
  13. package/esm/client/match_image_snapshot.d.ts.map +1 -0
  14. package/esm/client/match_image_snapshot.js +65 -0
  15. package/esm/client/match_image_snapshot.logic.d.ts +3 -0
  16. package/esm/client/match_image_snapshot.logic.d.ts.map +1 -0
  17. package/esm/client/match_image_snapshot.logic.js +11 -0
  18. package/esm/client/task_id.d.ts +3 -0
  19. package/esm/client/task_id.d.ts.map +1 -1
  20. package/esm/client/task_id.js +3 -0
  21. package/esm/client/vitest_browser_context_proxy.d.ts +32 -0
  22. package/esm/client/vitest_browser_context_proxy.d.ts.map +1 -0
  23. package/esm/client/vitest_browser_context_proxy.js +11 -0
  24. package/esm/client.d.ts +1 -1
  25. package/esm/client.d.ts.map +1 -1
  26. package/esm/client.js +1 -1
  27. package/esm/config/vis.d.ts +2 -0
  28. package/esm/config/vis.d.ts.map +1 -1
  29. package/esm/presets/auto.d.ts +1 -1
  30. package/esm/presets/auto.d.ts.map +1 -1
  31. package/esm/presets/auto.js +0 -1
  32. package/esm/presets/manual.d.ts +1 -1
  33. package/esm/presets/manual.d.ts.map +1 -1
  34. package/esm/presets/manual.js +0 -1
  35. package/esm/server/browser_provider/playwright.js +1 -1
  36. package/esm/server/browser_provider/webdriverio.js +1 -1
  37. package/esm/server/commands/_assertions.d.ts +5 -0
  38. package/esm/server/commands/_assertions.d.ts.map +1 -0
  39. package/esm/server/commands/_assertions.js +11 -0
  40. package/esm/server/commands/extend.d.ts +5 -1
  41. package/esm/server/commands/extend.d.ts.map +1 -1
  42. package/esm/server/commands/extend.js +4 -0
  43. package/esm/server/commands/has_image_snapshot.d.ts.map +1 -1
  44. package/esm/server/commands/has_image_snapshot.js +2 -3
  45. package/esm/server/commands/image_snapshot_next_index.d.ts.map +1 -1
  46. package/esm/server/commands/image_snapshot_next_index.js +2 -3
  47. package/esm/server/commands/match_image_snapshot.d.ts.map +1 -1
  48. package/esm/server/commands/match_image_snapshot.js +9 -31
  49. package/esm/server/commands/prepare_image_snapshot_comparison.d.ts +20 -0
  50. package/esm/server/commands/prepare_image_snapshot_comparison.d.ts.map +1 -0
  51. package/esm/server/commands/prepare_image_snapshot_comparison.js +31 -0
  52. package/esm/server/commands/setup_vis_suite.d.ts.map +1 -1
  53. package/esm/server/commands/setup_vis_suite.js +2 -0
  54. package/esm/server/commands/write_image_snapshot.d.ts +12 -0
  55. package/esm/server/commands/write_image_snapshot.d.ts.map +1 -0
  56. package/esm/server/commands/write_image_snapshot.js +9 -0
  57. package/esm/server/snapshot.d.ts +7 -0
  58. package/esm/server/snapshot.d.ts.map +1 -0
  59. package/esm/server/snapshot.js +27 -0
  60. package/esm/server/vis_context.d.ts.map +1 -1
  61. package/esm/server/vis_context.logic.d.ts +1 -1
  62. package/esm/server/vis_context.logic.d.ts.map +1 -1
  63. package/esm/shared/compare_image.d.ts +6 -0
  64. package/esm/shared/compare_image.d.ts.map +1 -0
  65. package/esm/shared/compare_image.js +10 -0
  66. package/esm/shared/convert_threshold_unit.js +1 -1
  67. package/esm/testing/stubBrowserCommandContext.d.ts +3 -0
  68. package/esm/testing/stubBrowserCommandContext.d.ts.map +1 -0
  69. package/esm/testing/stubBrowserCommandContext.js +2 -0
  70. package/esm/testing.d.ts +1 -0
  71. package/esm/testing.d.ts.map +1 -1
  72. package/esm/testing.js +1 -0
  73. package/package.json +3 -2
  74. package/readme.md +22 -4
  75. package/src/client/align_images.ts +11 -0
  76. package/src/client/expect/to_match_image_snapshot.ts +2 -17
  77. package/src/client/image_data.ts +36 -0
  78. package/src/client/image_resizer.ts +59 -0
  79. package/src/client/match_image_snapshot.logic.ts +13 -0
  80. package/src/client/match_image_snapshot.ts +87 -0
  81. package/src/client/task_id.ts +3 -0
  82. package/src/client/vitest_browser_context_proxy.ts +44 -0
  83. package/src/client.ts +1 -1
  84. package/src/presets/auto.ts +0 -1
  85. package/src/presets/manual.ts +0 -1
  86. package/src/server/browser_provider/playwright.ts +1 -1
  87. package/src/server/browser_provider/webdriverio.ts +1 -1
  88. package/src/server/commands/_assertions.ts +18 -0
  89. package/src/server/commands/extend.ts +9 -0
  90. package/src/server/commands/has_image_snapshot.ts +2 -3
  91. package/src/server/commands/image_snapshot_next_index.ts +2 -3
  92. package/src/server/commands/match_image_snapshot.ts +17 -46
  93. package/src/server/commands/prepare_image_snapshot_comparison.ts +54 -0
  94. package/src/server/commands/setup_vis_suite.ts +3 -0
  95. package/src/server/commands/write_image_snapshot.ts +26 -0
  96. package/src/server/snapshot.ts +42 -0
  97. package/src/server/vis_context.logic.ts +2 -2
  98. package/src/shared/compare_image.ts +20 -0
  99. package/src/shared/convert_threshold_unit.ts +1 -1
  100. package/src/testing/stubBrowserCommandContext.ts +4 -0
  101. package/src/testing.ts +1 -0
  102. package/esm/client/expect/to_match_image_snapshot.logic.d.ts +0 -2
  103. package/esm/client/expect/to_match_image_snapshot.logic.d.ts.map +0 -1
  104. package/esm/client/expect/to_match_image_snapshot.logic.js +0 -11
  105. package/esm/server/commands/is_ci.d.ts +0 -2
  106. package/esm/server/commands/is_ci.d.ts.map +0 -1
  107. package/esm/server/commands/is_ci.js +0 -6
  108. package/esm/server/compare_image.d.ts +0 -8
  109. package/esm/server/compare_image.d.ts.map +0 -1
  110. package/esm/server/compare_image.js +0 -16
  111. package/src/client/expect/to_match_image_snapshot.logic.ts +0 -11
  112. package/src/server/commands/is_ci.ts +0 -7
  113. package/src/server/compare_image.ts +0 -34
@@ -5,7 +5,7 @@ export function webdriverio(context: BrowserCommandContext): BrowserApi {
5
5
  const page = (context.provider as any).browser!
6
6
  return {
7
7
  async takeScreenshot(filePath, selector) {
8
- const element = await page.$(`${selector ?? 'body'}`)
8
+ const element = await page.$(`${selector}`)
9
9
  return element.saveScreenshot(filePath)
10
10
  },
11
11
  }
@@ -0,0 +1,18 @@
1
+ import { isAbsolute } from 'pathe'
2
+ import type { RequiredPick } from 'type-plus'
3
+ import type { BrowserCommandContext } from 'vitest/node'
4
+
5
+ export function assertTestPathDefined(
6
+ context: BrowserCommandContext,
7
+ commandName: string,
8
+ ): asserts context is RequiredPick<BrowserCommandContext, 'testPath'> {
9
+ if (!context.testPath) {
10
+ throw new Error(`'commands.${commandName}' requires testPath to be defined`)
11
+ }
12
+ }
13
+
14
+ export function assertIsRelativePath(relativeFilePath: string, propName: string) {
15
+ if (isAbsolute(relativeFilePath)) {
16
+ throw new Error(`'${propName}' must be a relative path`)
17
+ }
18
+ }
@@ -1,13 +1,20 @@
1
1
  import { type HasImageSnapshotCommand, hasImageSnapshot } from './has_image_snapshot.ts'
2
2
  import { type ImageSnapshotNextIndexCommand, imageSnapshotNextIndex } from './image_snapshot_next_index.ts'
3
3
  import { type MatchImageSnapshotCommand, matchImageSnapshot } from './match_image_snapshot.ts'
4
+ import {
5
+ type PrepareImageSnapshotComparisonCommand,
6
+ prepareImageSnapshotComparison,
7
+ } from './prepare_image_snapshot_comparison.ts'
4
8
  import { type SetupVisSuiteCommand, setupVisSuite } from './setup_vis_suite.ts'
9
+ import { type WriteImageSnapshotCommand, writeImageSnapshot } from './write_image_snapshot.ts'
5
10
 
6
11
  declare module '@vitest/browser/context' {
7
12
  interface BrowserCommands
8
13
  extends SetupVisSuiteCommand,
9
14
  ImageSnapshotNextIndexCommand,
10
15
  HasImageSnapshotCommand,
16
+ PrepareImageSnapshotComparisonCommand,
17
+ WriteImageSnapshotCommand,
11
18
  MatchImageSnapshotCommand {}
12
19
  }
13
20
 
@@ -16,4 +23,6 @@ export const commands = {
16
23
  imageSnapshotNextIndex,
17
24
  hasImageSnapshot,
18
25
  matchImageSnapshot,
26
+ prepareImageSnapshotComparison,
27
+ writeImageSnapshot,
19
28
  }
@@ -1,5 +1,6 @@
1
1
  import type { BrowserCommand } from 'vitest/node'
2
2
  import { visContext } from '../vis_context.ts'
3
+ import { assertTestPathDefined } from './_assertions.ts'
3
4
 
4
5
  export interface HasImageSnapshotCommand {
5
6
  hasImageSnapshot(taskId: string, snapshotId?: string | undefined): Promise<boolean>
@@ -10,9 +11,7 @@ export const hasImageSnapshot: BrowserCommand<[taskId: string, snapshotId?: stri
10
11
  taskId,
11
12
  snapshotId,
12
13
  ) => {
13
- if (!context.testPath) {
14
- throw new Error('Cannot take snapshot without testPath')
15
- }
14
+ assertTestPathDefined(context, 'hasImageSnapshot')
16
15
 
17
16
  return visContext.hasImageSnapshot(context.testPath, taskId, snapshotId)
18
17
  }
@@ -1,5 +1,6 @@
1
1
  import type { BrowserCommand } from 'vitest/node'
2
2
  import { visContext } from '../vis_context.ts'
3
+ import { assertTestPathDefined } from './_assertions.ts'
3
4
 
4
5
  export interface ImageSnapshotNextIndexCommand {
5
6
  /**
@@ -9,9 +10,7 @@ export interface ImageSnapshotNextIndexCommand {
9
10
  }
10
11
 
11
12
  export const imageSnapshotNextIndex: BrowserCommand<[taskId: string]> = async (context, taskId) => {
12
- if (!context.testPath) {
13
- throw new Error('Cannot take snapshot without testPath')
14
- }
13
+ assertTestPathDefined(context, 'imageSnapshotNextIndex')
15
14
 
16
15
  return visContext.getTaskCount(context.testPath, taskId)
17
16
  }
@@ -1,10 +1,10 @@
1
1
  import dedent from 'dedent'
2
2
  import ci from 'is-ci'
3
- import { mkdirp } from 'mkdirp'
4
- import { dirname, resolve } from 'pathe'
3
+ import { resolve } from 'pathe'
5
4
  import { PNG } from 'pngjs'
6
- import type { BrowserCommand, BrowserCommandContext } from 'vitest/node'
5
+ import type { BrowserCommand } from 'vitest/node'
7
6
  import { isBase64String } from '../../shared/base64.ts'
7
+ import { compareImage } from '../../shared/compare_image.ts'
8
8
  import { getMaxSize } from '../../shared/get_max_size.ts'
9
9
  import { isSameSize } from '../../shared/is_same_size.ts'
10
10
  import type {
@@ -12,10 +12,10 @@ import type {
12
12
  ImageSnapshotIdOptions,
13
13
  ImageSnapshotTimeoutOptions,
14
14
  } from '../../shared/types.ts'
15
- import { browserApi } from '../browser_provider/browser_api.ts'
16
- import { compareImage } from '../compare_image.ts'
17
15
  import { file } from '../file.ts'
16
+ import { takeSnapshot, takeSnapshotByBrowser, writeSnapshot, writeSnapshotBuffer } from '../snapshot.ts'
18
17
  import { visContext } from '../vis_context.ts'
18
+ import { assertTestPathDefined } from './_assertions.ts'
19
19
 
20
20
  export interface MatchImageSnapshotCommand {
21
21
  matchImageSnapshot: (
@@ -38,9 +38,7 @@ export interface MatchImageSnapshotOptions
38
38
  export const matchImageSnapshot: BrowserCommand<
39
39
  [taskId: string, subject: string, options?: MatchImageSnapshotOptions | undefined]
40
40
  > = async (context, taskId, subject, options) => {
41
- if (!context.testPath) {
42
- throw new Error('Cannot match snapshot without testPath')
43
- }
41
+ assertTestPathDefined(context, 'matchImageSnapshot')
44
42
 
45
43
  // vitest:browser passes in `null` when not defined
46
44
  if (!options) options = {}
@@ -57,12 +55,20 @@ export const matchImageSnapshot: BrowserCommand<
57
55
  return
58
56
  }
59
57
 
60
- const resultBuffer = await takeSnapshot(context, subject, info.resultPath, options)
58
+ const resultBuffer = await takeSnapshot(context, info.resultPath, subject, options)
61
59
  const baselineImage = PNG.sync.read(baselineBuffer, { skipRescale: true, checkCRC: false })
62
60
  const resultImage = PNG.sync.read(resultBuffer, { skipRescale: true, checkCRC: false })
63
61
  const [baselineAlignedImage, resultAlignedImage] = alignImageSizes(baselineImage, resultImage)
64
-
65
- const { pass, diffAmount, diffImage } = compareImage(baselineAlignedImage, resultAlignedImage, options)
62
+ const { width, height } = baselineAlignedImage
63
+ const diffImage = new PNG({ width, height })
64
+ const { pass, diffAmount } = compareImage(
65
+ baselineAlignedImage.data,
66
+ resultAlignedImage.data,
67
+ diffImage.data,
68
+ width,
69
+ height,
70
+ options,
71
+ )
66
72
  if (pass) {
67
73
  if (sizeNotChanged(baselineImage, baselineAlignedImage) && sizeNotChanged(resultImage, resultAlignedImage)) {
68
74
  return
@@ -103,41 +109,6 @@ export const matchImageSnapshot: BrowserCommand<
103
109
  )
104
110
  }
105
111
 
106
- async function takeSnapshot(
107
- context: BrowserCommandContext,
108
- subject: string,
109
- filePath: string,
110
- options: ImageSnapshotTimeoutOptions | undefined,
111
- ) {
112
- if (isBase64String(subject)) {
113
- await writeSnapshot(filePath, subject)
114
- return Buffer.from(subject, 'base64')
115
- }
116
- return takeSnapshotByBrowser(context, filePath, subject, options)
117
- }
118
-
119
- async function takeSnapshotByBrowser(
120
- context: BrowserCommandContext,
121
- filePath: string,
122
- subject: string,
123
- options: ImageSnapshotTimeoutOptions | undefined,
124
- ) {
125
- await mkdirp(dirname(filePath))
126
- const browser = browserApi(context)
127
- return browser.takeScreenshot(filePath, subject, {
128
- timeout: options?.timeout,
129
- })
130
- }
131
-
132
- async function writeSnapshot(filePath: string, subject: string) {
133
- await mkdirp(dirname(filePath))
134
- await file.writeFile(filePath, subject, { encoding: 'base64' })
135
- }
136
- async function writeSnapshotBuffer(filePath: string, subject: Buffer) {
137
- await mkdirp(dirname(filePath))
138
- await file.writeFile(filePath, subject)
139
- }
140
-
141
112
  function alignImageSizes(baseline: PNG, result: PNG) {
142
113
  if (isSameSize(baseline, result)) return [baseline, result] as const
143
114
 
@@ -0,0 +1,54 @@
1
+ import ci from 'is-ci'
2
+ import type { BrowserCommand } from 'vitest/node'
3
+ import { isBase64String } from '../../shared/base64.ts'
4
+ import { file } from '../file.ts'
5
+ import { takeSnapshot, takeSnapshotByBrowser, writeSnapshot } from '../snapshot.ts'
6
+ import { visContext } from '../vis_context.ts'
7
+ import { assertTestPathDefined } from './_assertions.ts'
8
+ import type { MatchImageSnapshotOptions } from './match_image_snapshot.ts'
9
+
10
+ type ImageSnapshotComparisonInfo = {
11
+ projectRoot: string
12
+ baselinePath: string
13
+ resultPath: string
14
+ diffPath: string
15
+ baseline: string
16
+ result: string
17
+ }
18
+
19
+ export interface PrepareImageSnapshotComparisonCommand {
20
+ prepareImageSnapshotComparison: (
21
+ taskId: string | undefined,
22
+ subject: string,
23
+ options?: MatchImageSnapshotOptions | undefined,
24
+ ) => Promise<ImageSnapshotComparisonInfo | undefined>
25
+ }
26
+
27
+ export const prepareImageSnapshotComparison: BrowserCommand<
28
+ [taskId: string, snapshotId: string, options?: MatchImageSnapshotOptions | undefined]
29
+ > = async (context, taskId, subject, options) => {
30
+ assertTestPathDefined(context, 'prepareImageSnapshotComparison')
31
+
32
+ // vitest:browser passes in `null` when not defined
33
+ if (!options) options = {}
34
+ options.timeout = options.timeout ?? (ci ? 30000 : 5000)
35
+
36
+ const info = visContext.getSnapshotInfo(context.testPath, taskId, options)
37
+ const baselineBuffer = await file.tryReadFile(info.baselinePath)
38
+ if (!baselineBuffer) {
39
+ if (isBase64String(subject)) {
40
+ await writeSnapshot(info.baselinePath, subject)
41
+ } else {
42
+ await takeSnapshotByBrowser(context, info.baselinePath, subject, options)
43
+ }
44
+ return
45
+ }
46
+
47
+ const resultBuffer = await takeSnapshot(context, info.resultPath, subject, options)
48
+ return {
49
+ ...info,
50
+ projectRoot: context.project.runner.root,
51
+ baseline: baselineBuffer.toString('base64'),
52
+ result: resultBuffer.toString('base64'),
53
+ }
54
+ }
@@ -1,5 +1,6 @@
1
1
  import type { BrowserCommand } from 'vitest/node'
2
2
  import { visContext } from '../vis_context.ts'
3
+ import { assertTestPathDefined } from './_assertions.ts'
3
4
 
4
5
  export interface SetupVisSuiteCommand {
5
6
  /**
@@ -13,5 +14,7 @@ export interface SetupVisSuiteCommand {
13
14
  }
14
15
 
15
16
  export const setupVisSuite: BrowserCommand<[]> = async (context) => {
17
+ assertTestPathDefined(context, 'setupVisSuite')
18
+
16
19
  await visContext.setupSuite(context)
17
20
  }
@@ -0,0 +1,26 @@
1
+ import { mkdirp } from 'mkdirp'
2
+ import { dirname, isAbsolute } from 'pathe'
3
+ import type { BrowserCommand } from 'vitest/node'
4
+ import { file } from '../file.ts'
5
+ import { assertIsRelativePath } from './_assertions.ts'
6
+
7
+ export interface WriteImageSnapshotCommand {
8
+ /**
9
+ * Writes the image snapshot to the file system.
10
+ * @param relativeFilePath The file path to write the image snapshot to.
11
+ * It is relative to the project root.
12
+ * @param imageBase64 The base64 encoded image.
13
+ */
14
+ writeImageSnapshot(relativeFilePath: string, imageBase64: string): Promise<void>
15
+ }
16
+
17
+ export const writeImageSnapshot: BrowserCommand<[relativeFilePath: string, imageBase64: string]> = async (
18
+ _,
19
+ relativeFilePath,
20
+ imageBase64,
21
+ ) => {
22
+ assertIsRelativePath(relativeFilePath, 'relativeFilePath')
23
+
24
+ await mkdirp(dirname(relativeFilePath))
25
+ await file.writeFile(relativeFilePath, imageBase64, { encoding: 'base64' })
26
+ }
@@ -0,0 +1,42 @@
1
+ import { mkdirp } from 'mkdirp'
2
+ import { dirname } from 'pathe'
3
+ import type { BrowserCommandContext } from 'vitest/node'
4
+ import type { ImageSnapshotTimeoutOptions } from '../client.ts'
5
+ import { isBase64String } from '../shared/base64.ts'
6
+ import { browserApi } from './browser_provider/browser_api.ts'
7
+ import { file } from './file.js'
8
+
9
+ export async function takeSnapshot(
10
+ context: BrowserCommandContext,
11
+ filePath: string,
12
+ subject: string,
13
+ options: ImageSnapshotTimeoutOptions | undefined,
14
+ ) {
15
+ if (isBase64String(subject)) {
16
+ await writeSnapshot(filePath, subject)
17
+ return Buffer.from(subject, 'base64')
18
+ }
19
+ return takeSnapshotByBrowser(context, filePath, subject, options)
20
+ }
21
+
22
+ export async function takeSnapshotByBrowser(
23
+ context: BrowserCommandContext,
24
+ filePath: string,
25
+ subject: string,
26
+ options: ImageSnapshotTimeoutOptions | undefined,
27
+ ) {
28
+ await mkdirp(dirname(filePath))
29
+ const browser = browserApi(context)
30
+ return browser.takeScreenshot(filePath, subject ?? 'body', {
31
+ timeout: options?.timeout,
32
+ })
33
+ }
34
+
35
+ export async function writeSnapshot(filePath: string, subject: string) {
36
+ await mkdirp(dirname(filePath))
37
+ await file.writeFile(filePath, subject, { encoding: 'base64' })
38
+ }
39
+ export async function writeSnapshotBuffer(filePath: string, subject: Buffer) {
40
+ await mkdirp(dirname(filePath))
41
+ await file.writeFile(filePath, subject)
42
+ }
@@ -17,7 +17,7 @@ export type PartialBrowserCommandContext = {
17
17
  hookTimeout: number
18
18
  }
19
19
  }
20
- testPath: string | undefined
20
+ testPath: string
21
21
  }
22
22
 
23
23
  export function createVisContext() {
@@ -51,7 +51,7 @@ export function createVisContext() {
51
51
  await globalStateReady
52
52
  }
53
53
 
54
- const { suiteId, suite } = createSuite(state, context.testPath!, visOptions)
54
+ const { suiteId, suite } = createSuite(state, context.testPath, visOptions)
55
55
  state.suites[suiteId] = suite
56
56
  await Promise.allSettled([ctx.rimraf(suite.diffDir), ctx.rimraf(suite.resultDir)])
57
57
  },
@@ -0,0 +1,20 @@
1
+ import pixelmatch from 'pixelmatch'
2
+ import { convertThresholdUnit } from './convert_threshold_unit.ts'
3
+ import type { ImageSnapshotCompareOptions } from './types.ts'
4
+
5
+ export function compareImage(
6
+ img1: Uint8ClampedArray | Buffer,
7
+ img2: Uint8ClampedArray | Buffer,
8
+ output: Uint8ClampedArray | Buffer,
9
+ width: number,
10
+ height: number,
11
+ { failureThreshold = 0, failureThresholdType = 'pixel', diffOptions }: ImageSnapshotCompareOptions = {},
12
+ ) {
13
+ const pixelDiff = pixelmatch(img1, img2, output, width, height, diffOptions)
14
+ const diffAmount = convertThresholdUnit({ failureThresholdType, width, height }, pixelDiff)
15
+
16
+ return {
17
+ pass: diffAmount <= failureThreshold,
18
+ diffAmount,
19
+ }
20
+ }
@@ -8,6 +8,6 @@ export function convertThresholdUnit(
8
8
  case 'percent':
9
9
  return (pixelDiff / (width * height)) * 100
10
10
  default:
11
- throw new Error(`Invalid failureThresholdType: ${failureThresholdType}`)
11
+ throw new Error(`Unsupported failureThresholdType: ${failureThresholdType}`)
12
12
  }
13
13
  }
@@ -0,0 +1,4 @@
1
+ import { stub } from 'type-plus'
2
+ import type { BrowserCommandContext } from 'vitest/node'
3
+
4
+ export const stubBrowserCommandContext = stub.build<BrowserCommandContext>({})
package/src/testing.ts CHANGED
@@ -1 +1,2 @@
1
1
  export * from './testing/constants.ts'
2
+ export * from './testing/stubBrowserCommandContext.ts'
@@ -1,2 +0,0 @@
1
- export declare function parseImageSnapshotSubject(subject: any): any;
2
- //# sourceMappingURL=to_match_image_snapshot.logic.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"to_match_image_snapshot.logic.d.ts","sourceRoot":"","sources":["../../../src/client/expect/to_match_image_snapshot.logic.ts"],"names":[],"mappings":"AAGA,wBAAgB,yBAAyB,CAAC,OAAO,EAAE,GAAG,OAOrD"}
@@ -1,11 +0,0 @@
1
- import { isBase64String } from "../../shared/base64.js";
2
- import { convertElementToCssSelector } from "../selector.js";
3
- export function parseImageSnapshotSubject(subject) {
4
- if (subject instanceof Element)
5
- return convertElementToCssSelector(subject);
6
- if (subject?.['selector'])
7
- return subject['selector'];
8
- if (isBase64String(subject))
9
- return subject;
10
- throw new Error(`'toMatchImageSnapshot()' expects the subject to be an element, locator, or image encoded in base64 string, but got: ${subject}`);
11
- }
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=is_ci.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"is_ci.d.ts","sourceRoot":"","sources":["../../../src/server/commands/is_ci.ts"],"names":[],"mappings":""}
@@ -1,6 +0,0 @@
1
- // import ci from 'is-ci'
2
- export {};
3
- // export interface IsCICommand {
4
- // isCI: () => Promise<boolean>
5
- // }
6
- // export const isCI = async () => ci
@@ -1,8 +0,0 @@
1
- import { PNG } from 'pngjs';
2
- import type { ImageSnapshotCompareOptions } from '../shared/types.ts';
3
- export declare function compareImage(baselineImage: PNG, resultImage: PNG, { failureThreshold, failureThresholdType, diffOptions }?: ImageSnapshotCompareOptions): {
4
- pass: boolean;
5
- diffAmount: number;
6
- diffImage: PNG;
7
- };
8
- //# sourceMappingURL=compare_image.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"compare_image.d.ts","sourceRoot":"","sources":["../../src/server/compare_image.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,GAAG,EAAE,MAAM,OAAO,CAAA;AAE3B,OAAO,KAAK,EAAE,2BAA2B,EAAE,MAAM,oBAAoB,CAAA;AAErE,wBAAgB,YAAY,CAC3B,aAAa,EAAE,GAAG,EAClB,WAAW,EAAE,GAAG,EAChB,EAAE,gBAAoB,EAAE,oBAA8B,EAAE,WAAW,EAAE,GAAE,2BAAgC;;;;EAyBvG"}
@@ -1,16 +0,0 @@
1
- import pixelmatch from 'pixelmatch';
2
- import { PNG } from 'pngjs';
3
- import { convertThresholdUnit } from "../shared/convert_threshold_unit.js";
4
- export function compareImage(baselineImage, resultImage, { failureThreshold = 0, failureThresholdType = 'pixel', diffOptions } = {}) {
5
- const diffImage = new PNG({
6
- width: baselineImage.width,
7
- height: baselineImage.height,
8
- });
9
- const pixelDiff = pixelmatch(resultImage.data, baselineImage.data, diffImage.data, baselineImage.width, baselineImage.height, diffOptions);
10
- const diffAmount = convertThresholdUnit({ failureThresholdType, width: baselineImage.width, height: baselineImage.height }, pixelDiff);
11
- return {
12
- pass: diffAmount <= failureThreshold,
13
- diffAmount,
14
- diffImage,
15
- };
16
- }
@@ -1,11 +0,0 @@
1
- import { isBase64String } from '../../shared/base64.ts'
2
- import { convertElementToCssSelector } from '../selector.ts'
3
-
4
- export function parseImageSnapshotSubject(subject: any) {
5
- if (subject instanceof Element) return convertElementToCssSelector(subject)
6
- if (subject?.['selector']) return subject['selector']
7
- if (isBase64String(subject)) return subject
8
- throw new Error(
9
- `'toMatchImageSnapshot()' expects the subject to be an element, locator, or image encoded in base64 string, but got: ${subject}`,
10
- )
11
- }
@@ -1,7 +0,0 @@
1
- // import ci from 'is-ci'
2
-
3
- // export interface IsCICommand {
4
- // isCI: () => Promise<boolean>
5
- // }
6
-
7
- // export const isCI = async () => ci
@@ -1,34 +0,0 @@
1
- import pixelmatch from 'pixelmatch'
2
- import { PNG } from 'pngjs'
3
- import { convertThresholdUnit } from '../shared/convert_threshold_unit.ts'
4
- import type { ImageSnapshotCompareOptions } from '../shared/types.ts'
5
-
6
- export function compareImage(
7
- baselineImage: PNG,
8
- resultImage: PNG,
9
- { failureThreshold = 0, failureThresholdType = 'pixel', diffOptions }: ImageSnapshotCompareOptions = {},
10
- ) {
11
- const diffImage = new PNG({
12
- width: baselineImage.width,
13
- height: baselineImage.height,
14
- })
15
-
16
- const pixelDiff = pixelmatch(
17
- resultImage.data,
18
- baselineImage.data,
19
- diffImage.data,
20
- baselineImage.width,
21
- baselineImage.height,
22
- diffOptions,
23
- )
24
- const diffAmount = convertThresholdUnit(
25
- { failureThresholdType, width: baselineImage.width, height: baselineImage.height },
26
- pixelDiff,
27
- )
28
-
29
- return {
30
- pass: diffAmount <= failureThreshold,
31
- diffAmount,
32
- diffImage,
33
- }
34
- }