@jsenv/snapshot 1.5.7 → 2.0.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/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jsenv/snapshot",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "2.0.0",
|
|
4
4
|
"description": "Snapshot testing",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": {
|
|
@@ -39,9 +39,7 @@
|
|
|
39
39
|
"@jsenv/urls": "2.2.11",
|
|
40
40
|
"@jsenv/utils": "2.1.1",
|
|
41
41
|
"pixelmatch": "6.0.0",
|
|
42
|
-
"prettier": "3.3.3"
|
|
43
|
-
},
|
|
44
|
-
"devDependencies": {
|
|
42
|
+
"prettier": "3.3.3",
|
|
45
43
|
"strip-ansi": "7.1.0"
|
|
46
44
|
}
|
|
47
45
|
}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { readdirSync, statSync, readFileSync } from "node:fs";
|
|
2
|
+
import { fileURLToPath } from "node:url";
|
|
2
3
|
import { URL_META } from "@jsenv/url-meta";
|
|
3
4
|
import {
|
|
4
5
|
assertAndNormalizeDirectoryUrl,
|
|
@@ -19,18 +20,32 @@ import {
|
|
|
19
20
|
ExtraFileAssertionError,
|
|
20
21
|
FileContentAssertionError,
|
|
21
22
|
} from "./errors.js";
|
|
23
|
+
import { replaceFluctuatingValues } from "./replace_fluctuating_values.js";
|
|
22
24
|
import { comparePngFiles } from "./compare_png_files.js";
|
|
23
25
|
|
|
24
26
|
export const takeFileSnapshot = (fileUrl) => {
|
|
25
27
|
fileUrl = assertAndNormalizeFileUrl(fileUrl);
|
|
26
28
|
const fileSnapshot = createFileSnapshot(fileUrl);
|
|
27
29
|
removeFileSync(fileUrl, { allowUseless: true });
|
|
30
|
+
const compare = (throwWhenDiff = process.env.CI) => {
|
|
31
|
+
fileSnapshot.compare(createFileSnapshot(fileUrl), { throwWhenDiff });
|
|
32
|
+
};
|
|
28
33
|
return {
|
|
29
|
-
compare
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
34
|
+
compare,
|
|
35
|
+
update: (
|
|
36
|
+
content,
|
|
37
|
+
{ mockFluctuatingValues = true, rootDirectoryUrl, throwWhenDiff } = {},
|
|
38
|
+
) => {
|
|
39
|
+
if (mockFluctuatingValues) {
|
|
40
|
+
content = replaceFluctuatingValues(content, {
|
|
41
|
+
cwdPath: rootDirectoryUrl
|
|
42
|
+
? fileURLToPath(rootDirectoryUrl)
|
|
43
|
+
: undefined,
|
|
44
|
+
cwdUrl: rootDirectoryUrl ? String(rootDirectoryUrl) : undefined,
|
|
45
|
+
});
|
|
46
|
+
}
|
|
33
47
|
writeFileSync(fileUrl, content);
|
|
48
|
+
compare(throwWhenDiff);
|
|
34
49
|
},
|
|
35
50
|
restore: () => {
|
|
36
51
|
if (fileSnapshot.empty) {
|
package/src/main.js
CHANGED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
// - Find all things looking like urls and replace with stable values
|
|
2
|
+
// - Find all things looking likes dates and replace with stable values
|
|
3
|
+
|
|
4
|
+
import stripAnsi from "strip-ansi";
|
|
5
|
+
import { pathToFileURL, fileURLToPath } from "node:url";
|
|
6
|
+
import { escapeRegexpSpecialChars } from "@jsenv/utils/src/string/escape_regexp_special_chars.js";
|
|
7
|
+
|
|
8
|
+
export const replaceFluctuatingValues = (
|
|
9
|
+
string,
|
|
10
|
+
{
|
|
11
|
+
removeAnsi = true,
|
|
12
|
+
rootDirectoryUrl = pathToFileURL(process.cwd()),
|
|
13
|
+
// for unit tests
|
|
14
|
+
rootDirectoryPath = fileURLToPath(rootDirectoryUrl),
|
|
15
|
+
isWindows = process.platform === "win32",
|
|
16
|
+
} = {},
|
|
17
|
+
) => {
|
|
18
|
+
if (removeAnsi) {
|
|
19
|
+
string = stripAnsi(string);
|
|
20
|
+
}
|
|
21
|
+
rootDirectoryUrl = String(rootDirectoryUrl);
|
|
22
|
+
if (rootDirectoryUrl[rootDirectoryUrl.length - 1] === "/") {
|
|
23
|
+
rootDirectoryUrl = rootDirectoryUrl.slice(0, -1);
|
|
24
|
+
}
|
|
25
|
+
string = string.replaceAll(rootDirectoryUrl, "file:///cwd()");
|
|
26
|
+
if (isWindows) {
|
|
27
|
+
const windowPathRegex = new RegExp(
|
|
28
|
+
`${escapeRegexpSpecialChars(rootDirectoryPath)}(((?:\\\\(?:[\\w !#()-]+|[.]{1,2})+)*)(?:\\\\)?)`,
|
|
29
|
+
"gm",
|
|
30
|
+
);
|
|
31
|
+
string = string.replaceAll(windowPathRegex, (match, afterCwd) => {
|
|
32
|
+
return `cwd()${afterCwd.replaceAll("\\", "/")}`;
|
|
33
|
+
});
|
|
34
|
+
} else {
|
|
35
|
+
string = string.replaceAll(rootDirectoryPath, "cwd()");
|
|
36
|
+
}
|
|
37
|
+
string = replaceHttpUrls(string);
|
|
38
|
+
return string;
|
|
39
|
+
};
|
|
40
|
+
|
|
41
|
+
const replaceHttpUrls = (source) => {
|
|
42
|
+
return source.replace(/(?:https?|ftp):\/\/\S+/g, (match) => {
|
|
43
|
+
const lastChar = match[match.length - 1];
|
|
44
|
+
// hotfix because our url regex sucks a bit
|
|
45
|
+
const endsWithSeparationChar = lastChar === ")" || lastChar === ":";
|
|
46
|
+
if (endsWithSeparationChar) {
|
|
47
|
+
match = match.slice(0, -1);
|
|
48
|
+
}
|
|
49
|
+
try {
|
|
50
|
+
const urlObject = new URL(match);
|
|
51
|
+
if (urlObject.port) {
|
|
52
|
+
urlObject.port = 9999;
|
|
53
|
+
}
|
|
54
|
+
return urlObject.href;
|
|
55
|
+
} catch (e) {
|
|
56
|
+
return match;
|
|
57
|
+
}
|
|
58
|
+
});
|
|
59
|
+
};
|