Skip to content

Commit b58f98d

Browse files
committed
fix: support object/array-formed condition (#212)
1 parent 20b960a commit b58f98d

File tree

5 files changed

+449
-3
lines changed

5 files changed

+449
-3
lines changed

package-lock.json

Lines changed: 11 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,10 +17,12 @@
1717
],
1818
"dependencies": {
1919
"clone-deep": "^4.0.1",
20+
"flat": "^5.0.2",
2021
"wildcard": "^2.0.0"
2122
},
2223
"devDependencies": {
2324
"@types/estree": "0.0.48",
25+
"@types/flat": "^5.0.3",
2426
"husky": "^6.0.0",
2527
"prettier": "^2.3.1",
2628
"tsdx": "^0.14.1",

src/index.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import {
88
ICustomizeOptions,
99
Key,
1010
} from "./types";
11-
import { isPlainObject, isUndefined } from "./utils";
11+
import { isPlainObject, isSameCondition, isUndefined } from "./utils";
1212

1313
function merge<Configuration extends object>(
1414
firstConfiguration: Configuration | Configuration[],
@@ -156,7 +156,7 @@ function mergeWithRule({
156156

157157
const bMatches = b.filter((o) => {
158158
const matches = rulesToMatch.every(
159-
(rule) => ao[rule]?.toString() === o[rule]?.toString()
159+
(rule) => isSameCondition(ao[rule], o[rule])
160160
);
161161

162162
if (matches) {

src/utils.ts

Lines changed: 58 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
import { flatten } from "flat";
2+
13
function isRegex(o) {
24
return o instanceof RegExp;
35
}
@@ -21,4 +23,59 @@ function isUndefined(a) {
2123
return typeof a === "undefined";
2224
}
2325

24-
export { isRegex, isFunction, isPlainObject, isUndefined };
26+
/**
27+
* According to Webpack docs, a "test" should be the following:
28+
*
29+
* - A string
30+
* - A RegExp
31+
* - A function
32+
* - An array of conditions (may be nested)
33+
* - An object of conditions (may be nested)
34+
*
35+
* https://webpack.js.org/configuration/module/#condition
36+
*/
37+
function isSameCondition(a, b) {
38+
if (!a || !b) {
39+
return a === b;
40+
}
41+
if (
42+
typeof a === 'string' && typeof b === 'string' ||
43+
isRegex(a) && isRegex(b) ||
44+
isFunction(a) && isFunction(b)
45+
) {
46+
return a.toString() === b.toString();
47+
}
48+
49+
const entriesA = Object.entries(flatten<any, object>(a));
50+
const entriesB = Object.entries(flatten<any, object>(b));
51+
if (entriesA.length !== entriesB.length) {
52+
return false;
53+
}
54+
55+
for (let i = 0; i < entriesA.length; i++) {
56+
entriesA[i][0] = entriesA[i][0].replace(/\b\d+\b/g, "[]");
57+
entriesB[i][0] = entriesB[i][0].replace(/\b\d+\b/g, "[]");
58+
}
59+
60+
function cmp([k1, v1], [k2, v2]) {
61+
if (k1 < k2) return -1;
62+
if (k1 > k2) return 1;
63+
if (v1 < v2) return -1;
64+
if (v1 > v2) return 1;
65+
return 0;
66+
};
67+
entriesA.sort(cmp);
68+
entriesB.sort(cmp);
69+
70+
if (entriesA.length !== entriesB.length) {
71+
return false;
72+
}
73+
for (let i = 0; i < entriesA.length; i++) {
74+
if (entriesA[i][0] !== entriesB[i][0] || entriesA[i][1]?.toString() !== entriesB[i][1]?.toString()) {
75+
return false;
76+
}
77+
}
78+
return true;
79+
}
80+
81+
export { isRegex, isFunction, isPlainObject, isUndefined, isSameCondition };

0 commit comments

Comments
 (0)