@cronn/lib-file-snapshots 0.13.0 → 0.15.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/dist/index.d.ts CHANGED
@@ -81,46 +81,23 @@ declare class TextSerializer implements SnapshotSerializer {
81
81
  interface ValidationFileMatcherConfig {
82
82
  /**
83
83
  * Directory in which golden masters are stored
84
- *
85
- * @default "data/test/validation"
86
84
  */
87
- validationDir?: string;
85
+ validationDir: string;
88
86
  /**
89
87
  * Directory in which file snapshots from test runs are stored
90
- *
91
- * @default "data/test/output"
92
- */
93
- outputDir?: string;
94
- /**
95
- * The full path to the current test file
96
- *
97
- * @example "src/tests/feature.test.ts"
98
- */
99
- testPath: string;
100
- /**
101
- * The full path of titles describing the current test, including nested blocks
102
- *
103
- * @example ["test A", "when x, then y"]
104
- */
105
- titlePath: Array<string>;
106
- /**
107
- * Unique name of the file snapshot
108
- *
109
- * Used to distinguish multiple file snapshots within the same `test`.
110
88
  */
111
- name?: string;
89
+ outputDir: string;
112
90
  /**
113
- * The naming strategy to use for storing the file snapshot
91
+ * The full path to the snapshot file
114
92
  *
115
- * @default "file"
93
+ * @example "src/tests/feature/test/when_x_then_y"
116
94
  */
117
- namingStrategy?: SnapshotNamingStrategy;
95
+ filePath: string;
118
96
  /**
119
97
  * The serializer to use for the snapshot
120
98
  */
121
99
  serializer: SnapshotSerializer;
122
100
  }
123
- type SnapshotNamingStrategy = "file" | "fileSuffix";
124
101
  interface ValidationFileMatcherResult {
125
102
  actual: string;
126
103
  expected: string;
@@ -129,6 +106,12 @@ interface ValidationFileMatcherResult {
129
106
  message: () => string;
130
107
  writeFileSnapshots: () => void;
131
108
  }
109
+ type FilePathResolver = (params: FilePathResolverParams) => string;
110
+ interface FilePathResolverParams {
111
+ testPath: string;
112
+ titlePath: Array<string>;
113
+ name?: string;
114
+ }
132
115
 
133
116
  declare class ValidationFileMatcher {
134
117
  private readonly serializer;
@@ -138,15 +121,19 @@ declare class ValidationFileMatcher {
138
121
  get isValidationFileMissing(): boolean;
139
122
  matchFileSnapshot(actual: unknown): ValidationFileMatcherResult;
140
123
  private buildFilePaths;
141
- private applyNamingStrategy;
142
124
  private readValidationFile;
143
125
  private createMatcherResult;
144
126
  private writeFileSnapshots;
145
127
  }
146
128
 
129
+ declare function resolveNameAsFile(params: FilePathResolverParams): string;
130
+ declare function resolveNameAsFileSuffix(params: FilePathResolverParams): string;
131
+
132
+ declare function normalizeFileName(testName: string): string;
133
+
147
134
  declare function isString(value: unknown): value is string;
148
135
  declare function isArray(value: unknown): value is Array<unknown>;
149
136
  type PlainObject = Record<PropertyKey, unknown>;
150
137
  declare function isPlainObject(value: unknown): value is PlainObject;
151
138
 
152
- export { type JsonNormalizer, type JsonNormalizerContext, JsonSerializer, type PlainObject, type SnapshotNamingStrategy, type SnapshotSerializer, type TextNormalizer, TextSerializer, ValidationFileMatcher, type ValidationFileMatcherResult, isArray, isPlainObject, isString };
139
+ export { type FilePathResolver, type FilePathResolverParams, type JsonNormalizer, type JsonNormalizerContext, JsonSerializer, type PlainObject, type SnapshotSerializer, type TextNormalizer, TextSerializer, ValidationFileMatcher, type ValidationFileMatcherResult, isArray, isPlainObject, isString, normalizeFileName, resolveNameAsFile, resolveNameAsFileSuffix };
package/dist/index.js CHANGED
@@ -6,15 +6,15 @@ var EMOJI_REGEXP = /(?!(\*|#|\d))[\p{Extended_Pictographic}\p{Emoji_Component}]|
6
6
  function normalizeFileName(testName) {
7
7
  return testName.replaceAll(EMOJI_REGEXP, "").replaceAll(/[+*%~<>?!$#'"`|\\/()[\]{}]/g, "").replaceAll(/[\s.:,;]+/g, "_").replaceAll(/_{2,}/g, "_");
8
8
  }
9
- function readSnapshotFile(path3) {
10
- return fs.readFileSync(path3, { encoding: "utf8" });
9
+ function readSnapshotFile(path4) {
10
+ return fs.readFileSync(path4, { encoding: "utf8" });
11
11
  }
12
12
  function writeSnapshotFile(file, data) {
13
13
  mkdirRecursive(path.dirname(file));
14
14
  fs.writeFileSync(file, data, { encoding: "utf8" });
15
15
  }
16
- function mkdirRecursive(path3) {
17
- fs.mkdirSync(path3, { recursive: true });
16
+ function mkdirRecursive(path4) {
17
+ fs.mkdirSync(path4, { recursive: true });
18
18
  }
19
19
  function addTrailingNewLine(data) {
20
20
  return `${data}${NEW_LINE_SEPARATOR}`;
@@ -272,34 +272,13 @@ var ValidationFileMatcher = class {
272
272
  });
273
273
  }
274
274
  buildFilePaths(config) {
275
- const validationDir = config.validationDir ?? "data/test/validation";
276
- const outputDir = config.outputDir ?? "data/test/output";
277
- const normalizedTitlePath = config.titlePath.map(normalizeFileName);
278
- const relativeFilePath = path2.join(config.testPath, ...normalizedTitlePath);
279
- const relativeFilePathWithName = this.applyNamingStrategy(
280
- relativeFilePath,
281
- config.name,
282
- config.namingStrategy
283
- );
284
- const relativeFilePathWithExtension = `${relativeFilePathWithName}.${this.serializer.fileExtension}`;
275
+ const { validationDir, outputDir, filePath, serializer } = config;
276
+ const filePathWithExtension = `${filePath}.${serializer.fileExtension}`;
285
277
  return {
286
- outputFilePath: path2.join(outputDir, relativeFilePathWithExtension),
287
- validationFilePath: path2.join(
288
- validationDir,
289
- relativeFilePathWithExtension
290
- )
278
+ outputFilePath: path2.join(outputDir, filePathWithExtension),
279
+ validationFilePath: path2.join(validationDir, filePathWithExtension)
291
280
  };
292
281
  }
293
- applyNamingStrategy(filePath, snapshotName, namingStrategy = "file") {
294
- if (snapshotName === void 0) {
295
- return filePath;
296
- }
297
- const normalizedSnapshotName = normalizeFileName(snapshotName);
298
- if (namingStrategy === "fileSuffix") {
299
- return `${filePath}_${normalizedSnapshotName}`;
300
- }
301
- return path2.join(filePath, normalizedSnapshotName);
302
- }
303
282
  readValidationFile() {
304
283
  const { validationFilePath } = this.filePaths;
305
284
  if (!fs2.existsSync(validationFilePath)) {
@@ -329,11 +308,43 @@ does not match validation file '${validationFilePath}'`,
329
308
  }
330
309
  }
331
310
  };
311
+
312
+ // src/matcher/file-path-resolver.ts
313
+ import path3 from "path";
314
+ function resolveNameAsFile(params) {
315
+ return resolveFilePath(
316
+ params,
317
+ ({ basePath, normalizedName }) => path3.join(basePath, normalizedName)
318
+ );
319
+ }
320
+ function resolveNameAsFileSuffix(params) {
321
+ return resolveFilePath(
322
+ params,
323
+ ({ basePath, normalizedName }) => `${basePath}_${normalizedName}`
324
+ );
325
+ }
326
+ function resolveBasePath(params) {
327
+ const { testPath, titlePath } = params;
328
+ const normalizedTitlePath = titlePath.map(normalizeFileName);
329
+ return path3.join(testPath, ...normalizedTitlePath);
330
+ }
331
+ function resolveFilePath(params, resolveNamedFilePath) {
332
+ const { name, ...baseParams } = params;
333
+ const basePath = resolveBasePath(baseParams);
334
+ if (name === void 0) {
335
+ return basePath;
336
+ }
337
+ const normalizedName = normalizeFileName(name);
338
+ return resolveNamedFilePath({ basePath, normalizedName });
339
+ }
332
340
  export {
333
341
  JsonSerializer,
334
342
  TextSerializer,
335
343
  ValidationFileMatcher,
336
344
  isArray,
337
345
  isPlainObject,
338
- isString
346
+ isString,
347
+ normalizeFileName,
348
+ resolveNameAsFile,
349
+ resolveNameAsFileSuffix
339
350
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cronn/lib-file-snapshots",
3
- "version": "0.13.0",
3
+ "version": "0.15.0",
4
4
  "description": "The library agnostic core for testing file snapshots",
5
5
  "keywords": [
6
6
  "file snapshots"
@@ -33,15 +33,15 @@
33
33
  ],
34
34
  "devDependencies": {
35
35
  "@trivago/prettier-plugin-sort-imports": "5.2.2",
36
- "@types/node": "22.17.1",
36
+ "@types/node": "22.18.1",
37
37
  "@vitest/coverage-istanbul": "3.2.4",
38
- "eslint": "9.32.0",
38
+ "eslint": "9.35.0",
39
39
  "eslint-config-prettier": "10.1.8",
40
- "eslint-plugin-unused-imports": "4.1.4",
40
+ "eslint-plugin-unused-imports": "4.2.0",
41
41
  "prettier": "3.6.2",
42
42
  "tsup": "8.5.0",
43
- "typescript": "5.8.3",
44
- "typescript-eslint": "8.38.0",
43
+ "typescript": "5.9.2",
44
+ "typescript-eslint": "8.42.0",
45
45
  "vitest": "3.2.4",
46
46
  "@cronn/shared-configs": "0.0.0"
47
47
  },