@nordcraft/search 1.0.45 → 1.0.46
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/problems.worker.js +9 -3
- package/dist/problems.worker.js.map +1 -1
- package/dist/rules/logic/noStaticNodeCondition.js +29 -0
- package/dist/rules/logic/noStaticNodeCondition.js.map +1 -0
- package/dist/rules/logic/noStaticNodeCondition.test.js +274 -0
- package/dist/rules/logic/noStaticNodeCondition.test.js.map +1 -0
- package/dist/rules/logic/noUnnecessaryConditionFalsy.js +5 -1
- package/dist/rules/logic/noUnnecessaryConditionFalsy.js.map +1 -1
- package/dist/rules/logic/noUnnecessaryConditionTruthy.js +8 -4
- package/dist/rules/logic/noUnnecessaryConditionTruthy.js.map +1 -1
- package/dist/rules/logic/noUnnecessaryConditionTruthy.test.js +33 -4
- package/dist/rules/logic/noUnnecessaryConditionTruthy.test.js.map +1 -1
- package/dist/rules/noReferenceNodeRule.js +10 -8
- package/dist/rules/noReferenceNodeRule.js.map +1 -1
- package/dist/rules/noReferenceNodeRule.test.js +1 -1
- package/dist/rules/style/invalidStyleSyntaxRule.js +2 -2
- package/dist/rules/style/invalidStyleSyntaxRule.test.js +1 -1
- package/dist/util/contextlessEvaluateFormula.js +77 -0
- package/dist/util/contextlessEvaluateFormula.js.map +1 -0
- package/dist/util/contextlessEvaluateFormula.test.js +152 -0
- package/dist/util/contextlessEvaluateFormula.test.js.map +1 -0
- package/dist/util/removeUnused.fix.js +18 -1
- package/dist/util/removeUnused.fix.js.map +1 -1
- package/package.json +2 -2
- package/src/problems.worker.ts +16 -5
- package/src/rules/logic/noStaticNodeCondition.test.ts +290 -0
- package/src/rules/logic/noStaticNodeCondition.ts +43 -0
- package/src/rules/logic/noUnnecessaryConditionFalsy.ts +5 -4
- package/src/rules/logic/noUnnecessaryConditionTruthy.test.ts +37 -4
- package/src/rules/logic/noUnnecessaryConditionTruthy.ts +10 -8
- package/src/rules/noReferenceNodeRule.test.ts +1 -1
- package/src/rules/noReferenceNodeRule.ts +17 -10
- package/src/rules/style/invalidStyleSyntaxRule.test.ts +1 -1
- package/src/rules/style/invalidStyleSyntaxRule.ts +3 -3
- package/src/types.d.ts +3 -0
- package/src/util/contextlessEvaluateFormula.test.ts +190 -0
- package/src/util/contextlessEvaluateFormula.ts +110 -0
- package/src/util/removeUnused.fix.ts +29 -1
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import {} from '@nordcraft/core/dist/formula/formula';
|
|
2
|
+
/**
|
|
3
|
+
* Static evaluation of a formula.
|
|
4
|
+
*
|
|
5
|
+
* Can be used by issues to determine if a formula or sub-formula can be reduced to a static value.
|
|
6
|
+
* When sophisticated enough, it can be used during compile-time to reduce all static subgraphs of a formula to static values, greatly reducing payload and improving runtime performance.
|
|
7
|
+
*
|
|
8
|
+
* @returns {
|
|
9
|
+
* isStatic: boolean; // Whether the formula is static (i.e., does not depend on any variables, context AND only use pure formulas (no Random, Date, etc.))
|
|
10
|
+
* result: unknown; // The evaluated value of the formula
|
|
11
|
+
* }
|
|
12
|
+
*
|
|
13
|
+
* TODO: Make this function more capable of evaluating pure core formulas.
|
|
14
|
+
* TODO: Memoize the results (using path or a fast hash) to avoid re-evaluating any similar sub-graphs multiple times.
|
|
15
|
+
* TODO: Add a complex test-suite to ensure it works and develops as expected.
|
|
16
|
+
*/
|
|
17
|
+
export const contextlessEvaluateFormula = (formula) => {
|
|
18
|
+
// Very basic implementation, just to get started.
|
|
19
|
+
switch (formula.type) {
|
|
20
|
+
case 'value': {
|
|
21
|
+
return {
|
|
22
|
+
isStatic: true,
|
|
23
|
+
result: formula.value,
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
case 'array': {
|
|
27
|
+
const results = formula.arguments.map((arg) => contextlessEvaluateFormula(arg.formula));
|
|
28
|
+
return {
|
|
29
|
+
isStatic: results.every((res) => res.isStatic),
|
|
30
|
+
result: results.map((res) => res.result),
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
case 'record': {
|
|
34
|
+
const entries = Object.entries(formula.entries).map(([key, arg]) => [key, contextlessEvaluateFormula(arg.formula)]);
|
|
35
|
+
const results = entries.map(([, res]) => res);
|
|
36
|
+
return {
|
|
37
|
+
isStatic: results.every((res) => res.isStatic),
|
|
38
|
+
result: Object.fromEntries(entries.map(([key, res]) => [key, res.result])),
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
// Static if:
|
|
42
|
+
// - ALL conditions are static AND truthy
|
|
43
|
+
// - ANY condition is static and falsy
|
|
44
|
+
// - EMPTY argument list is always true
|
|
45
|
+
case 'and': {
|
|
46
|
+
const results = formula.arguments.map((arg) => contextlessEvaluateFormula(arg.formula));
|
|
47
|
+
const alwaysTrue = results.length === 0 ||
|
|
48
|
+
results.every((res) => res.isStatic && Boolean(res.result) === true);
|
|
49
|
+
const alwaysFalsy = results.some((res) => res.isStatic && Boolean(res.result) === false);
|
|
50
|
+
return {
|
|
51
|
+
isStatic: alwaysTrue || alwaysFalsy,
|
|
52
|
+
result: alwaysTrue ? true : alwaysFalsy ? false : undefined,
|
|
53
|
+
};
|
|
54
|
+
}
|
|
55
|
+
// Static if:
|
|
56
|
+
// - ANY condition is static AND truthy
|
|
57
|
+
// - ALL conditions are static AND falsy
|
|
58
|
+
// - EMPTY argument list is always false
|
|
59
|
+
case 'or': {
|
|
60
|
+
const results = formula.arguments.map((arg) => contextlessEvaluateFormula(arg.formula));
|
|
61
|
+
const alwaysFalsy = results.length === 0 ||
|
|
62
|
+
results.every((res) => res.isStatic && Boolean(res.result) === false);
|
|
63
|
+
const alwaysTrue = results.some((res) => res.isStatic && Boolean(res.result) === true);
|
|
64
|
+
return {
|
|
65
|
+
isStatic: alwaysTrue || alwaysFalsy,
|
|
66
|
+
result: alwaysFalsy ? false : alwaysTrue ? true : undefined,
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
default:
|
|
70
|
+
// For now, we assume that any other formula is not static.
|
|
71
|
+
return {
|
|
72
|
+
isStatic: false,
|
|
73
|
+
result: undefined,
|
|
74
|
+
};
|
|
75
|
+
}
|
|
76
|
+
};
|
|
77
|
+
//# sourceMappingURL=contextlessEvaluateFormula.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contextlessEvaluateFormula.js","sourceRoot":"","sources":["../../src/util/contextlessEvaluateFormula.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
import { describe, expect, test } from 'bun:test';
|
|
2
|
+
import { contextlessEvaluateFormula } from './contextlessEvaluateFormula';
|
|
3
|
+
describe('contextlessEvaluateFormula', () => {
|
|
4
|
+
test('should return `true` when the formula is a simple value formula', () => {
|
|
5
|
+
expect(contextlessEvaluateFormula({
|
|
6
|
+
type: 'value',
|
|
7
|
+
value: true,
|
|
8
|
+
})).toEqual({
|
|
9
|
+
isStatic: true,
|
|
10
|
+
result: true,
|
|
11
|
+
});
|
|
12
|
+
});
|
|
13
|
+
test('should not return a result and have `isStatic: false` when the formula uses a non-pure formula ("randomNumber", "Now")', () => {
|
|
14
|
+
expect(contextlessEvaluateFormula({
|
|
15
|
+
type: 'apply',
|
|
16
|
+
name: 'randomNumber',
|
|
17
|
+
arguments: [],
|
|
18
|
+
})).toEqual({
|
|
19
|
+
isStatic: false,
|
|
20
|
+
result: undefined,
|
|
21
|
+
});
|
|
22
|
+
expect(contextlessEvaluateFormula({
|
|
23
|
+
type: 'apply',
|
|
24
|
+
name: 'now',
|
|
25
|
+
arguments: [],
|
|
26
|
+
})).toEqual({
|
|
27
|
+
isStatic: false,
|
|
28
|
+
result: undefined,
|
|
29
|
+
});
|
|
30
|
+
});
|
|
31
|
+
test('should not return a result and have `isStatic: false` when the formula depends on a variable', () => {
|
|
32
|
+
expect(contextlessEvaluateFormula({
|
|
33
|
+
type: 'path',
|
|
34
|
+
path: ['Variables', 'myVariable'],
|
|
35
|
+
})).toEqual({
|
|
36
|
+
isStatic: false,
|
|
37
|
+
result: undefined,
|
|
38
|
+
});
|
|
39
|
+
});
|
|
40
|
+
test('should return a result and static for an array formula where all args are array or value types', () => {
|
|
41
|
+
expect(contextlessEvaluateFormula({
|
|
42
|
+
type: 'array',
|
|
43
|
+
arguments: [
|
|
44
|
+
{ formula: { type: 'value', value: 1 } },
|
|
45
|
+
{
|
|
46
|
+
formula: {
|
|
47
|
+
type: 'array',
|
|
48
|
+
arguments: [{ formula: { type: 'value', value: 2 } }],
|
|
49
|
+
},
|
|
50
|
+
},
|
|
51
|
+
],
|
|
52
|
+
})).toEqual({
|
|
53
|
+
isStatic: true,
|
|
54
|
+
result: [1, [2]],
|
|
55
|
+
});
|
|
56
|
+
});
|
|
57
|
+
test('should return `isStatic: false` for an array formula with a non-static argument', () => {
|
|
58
|
+
expect(contextlessEvaluateFormula({
|
|
59
|
+
type: 'array',
|
|
60
|
+
arguments: [
|
|
61
|
+
{ formula: { type: 'value', value: 1 } },
|
|
62
|
+
{ formula: { type: 'apply', name: 'randomNumber', arguments: [] } },
|
|
63
|
+
],
|
|
64
|
+
})).toEqual({
|
|
65
|
+
isStatic: false,
|
|
66
|
+
result: [
|
|
67
|
+
1,
|
|
68
|
+
undefined, // The second argument was not static
|
|
69
|
+
],
|
|
70
|
+
});
|
|
71
|
+
});
|
|
72
|
+
test('should be static true for `And` formulas with no arguments', () => {
|
|
73
|
+
expect(contextlessEvaluateFormula({
|
|
74
|
+
type: 'and',
|
|
75
|
+
arguments: [],
|
|
76
|
+
})).toEqual({
|
|
77
|
+
isStatic: true,
|
|
78
|
+
result: true,
|
|
79
|
+
});
|
|
80
|
+
});
|
|
81
|
+
test('should be static false for `Or` formulas with no arguments', () => {
|
|
82
|
+
expect(contextlessEvaluateFormula({
|
|
83
|
+
type: 'or',
|
|
84
|
+
arguments: [],
|
|
85
|
+
})).toEqual({
|
|
86
|
+
isStatic: true,
|
|
87
|
+
result: false,
|
|
88
|
+
});
|
|
89
|
+
});
|
|
90
|
+
test('should be static true for `And` formulas with all static truthy arguments', () => {
|
|
91
|
+
expect(contextlessEvaluateFormula({
|
|
92
|
+
type: 'and',
|
|
93
|
+
arguments: [
|
|
94
|
+
{ formula: { type: 'value', value: true } },
|
|
95
|
+
{ formula: { type: 'value', value: true } },
|
|
96
|
+
],
|
|
97
|
+
})).toEqual({
|
|
98
|
+
isStatic: true,
|
|
99
|
+
result: true,
|
|
100
|
+
});
|
|
101
|
+
});
|
|
102
|
+
test('should not be static for `And` where any dynamic value exist', () => {
|
|
103
|
+
expect(contextlessEvaluateFormula({
|
|
104
|
+
type: 'and',
|
|
105
|
+
arguments: [
|
|
106
|
+
{ formula: { type: 'value', value: true } },
|
|
107
|
+
{ formula: { type: 'apply', name: 'randomNumber', arguments: [] } },
|
|
108
|
+
],
|
|
109
|
+
})).toEqual({
|
|
110
|
+
isStatic: false,
|
|
111
|
+
result: undefined,
|
|
112
|
+
});
|
|
113
|
+
});
|
|
114
|
+
test('should be static false for `And` when any argument is static false, even when dynamic arguments exist', () => {
|
|
115
|
+
expect(contextlessEvaluateFormula({
|
|
116
|
+
type: 'and',
|
|
117
|
+
arguments: [
|
|
118
|
+
{ formula: { type: 'value', value: true } },
|
|
119
|
+
{ formula: { type: 'path', path: ['Variables', 'myVariable'] } },
|
|
120
|
+
{ formula: { type: 'value', value: false } },
|
|
121
|
+
],
|
|
122
|
+
})).toEqual({
|
|
123
|
+
isStatic: true,
|
|
124
|
+
result: false,
|
|
125
|
+
});
|
|
126
|
+
});
|
|
127
|
+
test('should not be static for `Or` when any argument is dynamic and all static are falsy', () => {
|
|
128
|
+
expect(contextlessEvaluateFormula({
|
|
129
|
+
type: 'or',
|
|
130
|
+
arguments: [
|
|
131
|
+
{ formula: { type: 'value', value: false } },
|
|
132
|
+
{ formula: { type: 'apply', name: 'randomNumber', arguments: [] } },
|
|
133
|
+
],
|
|
134
|
+
})).toEqual({
|
|
135
|
+
isStatic: false,
|
|
136
|
+
result: undefined,
|
|
137
|
+
});
|
|
138
|
+
});
|
|
139
|
+
test('should be static true for `Or` when any argument is static true, even when dynamic arguments exist', () => {
|
|
140
|
+
expect(contextlessEvaluateFormula({
|
|
141
|
+
type: 'or',
|
|
142
|
+
arguments: [
|
|
143
|
+
{ formula: { type: 'value', value: true } },
|
|
144
|
+
{ formula: { type: 'apply', name: 'randomNumber', arguments: [] } },
|
|
145
|
+
],
|
|
146
|
+
})).toEqual({
|
|
147
|
+
isStatic: true,
|
|
148
|
+
result: true,
|
|
149
|
+
});
|
|
150
|
+
});
|
|
151
|
+
});
|
|
152
|
+
//# sourceMappingURL=contextlessEvaluateFormula.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contextlessEvaluateFormula.test.js","sourceRoot":"","sources":["../../src/util/contextlessEvaluateFormula.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,3 +1,20 @@
|
|
|
1
|
-
import { omit } from '@nordcraft/core/dist/utils/collections';
|
|
1
|
+
import { get, omit, set } from '@nordcraft/core/dist/utils/collections';
|
|
2
2
|
export const removeFromPathFix = ({ path, files }) => omit(files, path);
|
|
3
|
+
/**
|
|
4
|
+
* Same as removeFromPathFix, but also removes the node from its parent's children.
|
|
5
|
+
*/
|
|
6
|
+
export const removeNodeFromPathFix = (data) => {
|
|
7
|
+
if (data.nodeType !== 'component-node') {
|
|
8
|
+
throw new Error('removeNodeFromPathFix can only be used on component nodes');
|
|
9
|
+
}
|
|
10
|
+
const componentNodesPath = data.path.slice(0, -1).map(String);
|
|
11
|
+
const filesWithoutNode = removeFromPathFix(data);
|
|
12
|
+
const nodes = get(filesWithoutNode, componentNodesPath);
|
|
13
|
+
for (const key in nodes) {
|
|
14
|
+
if (nodes[key].children?.includes(data.path[data.path.length - 1])) {
|
|
15
|
+
nodes[key].children = nodes[key].children.filter((p) => p !== data.path[data.path.length - 1]);
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
return set(filesWithoutNode, componentNodesPath, nodes);
|
|
19
|
+
};
|
|
3
20
|
//# sourceMappingURL=removeUnused.fix.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"removeUnused.fix.js","sourceRoot":"","sources":["../../src/util/removeUnused.fix.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"removeUnused.fix.js","sourceRoot":"","sources":["../../src/util/removeUnused.fix.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,GAAG,EAAE,MAAM,wCAAwC,CAAA;AAGvE,MAAM,CAAC,MAAM,iBAAiB,GAA0B,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,EAAE,EAAE,CAC1E,IAAI,CAAC,KAAK,EAAE,IAAI,CAAC,CAAA;AAEnB;;GAEG;AACH,MAAM,CAAC,MAAM,qBAAqB,GAA0B,CAAC,IAAI,EAAE,EAAE;IACnE,IAAI,IAAI,CAAC,QAAQ,KAAK,gBAAgB,EAAE,CAAC;QACvC,MAAM,IAAI,KAAK,CAAC,2DAA2D,CAAC,CAAA;IAC9E,CAAC;IAED,MAAM,kBAAkB,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,CAAA;IAC7D,MAAM,gBAAgB,GAAG,iBAAiB,CAAC,IAAI,CAAC,CAAA;IAChD,MAAM,KAAK,GAAG,GAAG,CAAC,gBAAgB,EAAE,kBAAkB,CAGrD,CAAA;IACD,KAAK,MAAM,GAAG,IAAI,KAAK,EAAE,CAAC;QACxB,IACE,KAAK,CAAC,GAAG,CAAC,CAAC,QAAQ,EAAE,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,CAAW,CAAC,EACxE,CAAC;YACD,KAAK,CAAC,GAAG,CAAC,CAAC,QAAQ,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,QAAQ,CAAC,MAAM,CAC9C,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,KAAK,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,CAAC,CAC7C,CAAA;QACH,CAAC;IACH,CAAC;IAED,OAAO,GAAG,CAAC,gBAAgB,EAAE,kBAAkB,EAAE,KAAK,CAAC,CAAA;AACzD,CAAC,CAAA"}
|
package/package.json
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"homepage": "https://github.com/nordcraftengine/nordcraft",
|
|
7
7
|
"dependencies": {
|
|
8
|
-
"@nordcraft/ssr": "1.0.
|
|
8
|
+
"@nordcraft/ssr": "1.0.46",
|
|
9
9
|
"jsondiffpatch": "0.7.3",
|
|
10
10
|
"postcss": "8.5.6"
|
|
11
11
|
},
|
|
@@ -19,5 +19,5 @@
|
|
|
19
19
|
"test:watch:only": "bun test --watch --only"
|
|
20
20
|
},
|
|
21
21
|
"files": ["dist", "src"],
|
|
22
|
-
"version": "1.0.
|
|
22
|
+
"version": "1.0.46"
|
|
23
23
|
}
|
package/src/problems.worker.ts
CHANGED
|
@@ -37,6 +37,7 @@ import { unknownFormulaRule } from './rules/formulas/unknownFormulaRule'
|
|
|
37
37
|
import { unknownProjectFormulaRule } from './rules/formulas/unknownProjectFormulaRule'
|
|
38
38
|
import { unknownRepeatIndexFormulaRule } from './rules/formulas/unknownRepeatIndexFormulaRule'
|
|
39
39
|
import { unknownRepeatItemFormulaRule } from './rules/formulas/unknownRepeatItemFormulaRule'
|
|
40
|
+
import { noStaticNodeCondition } from './rules/logic/noStaticNodeCondition'
|
|
40
41
|
import { noUnnecessaryConditionFalsy } from './rules/logic/noUnnecessaryConditionFalsy'
|
|
41
42
|
import { noUnnecessaryConditionTruthy } from './rules/logic/noUnnecessaryConditionTruthy'
|
|
42
43
|
import { noReferenceNodeRule } from './rules/noReferenceNodeRule'
|
|
@@ -162,6 +163,7 @@ const RULES = [
|
|
|
162
163
|
noReferenceProjectActionRule,
|
|
163
164
|
noReferenceProjectFormulaRule,
|
|
164
165
|
noReferenceVariableRule,
|
|
166
|
+
noStaticNodeCondition,
|
|
165
167
|
noUnnecessaryConditionFalsy,
|
|
166
168
|
noUnnecessaryConditionTruthy,
|
|
167
169
|
requireExtensionRule,
|
|
@@ -196,21 +198,25 @@ const RULES = [
|
|
|
196
198
|
]
|
|
197
199
|
|
|
198
200
|
interface FindProblemsArgs {
|
|
201
|
+
id: string
|
|
199
202
|
files: ProjectFiles
|
|
200
203
|
options?: Options
|
|
201
204
|
}
|
|
202
205
|
|
|
203
206
|
interface FixProblemsArgs {
|
|
207
|
+
id: string
|
|
204
208
|
files: ProjectFiles
|
|
205
209
|
options?: Options
|
|
206
210
|
fixRule: Code
|
|
207
211
|
fixType: FixType
|
|
208
|
-
id: string
|
|
209
212
|
}
|
|
210
213
|
|
|
211
214
|
type Message = FindProblemsArgs | FixProblemsArgs
|
|
212
215
|
|
|
213
|
-
|
|
216
|
+
interface FindProblemsResponse {
|
|
217
|
+
id: string
|
|
218
|
+
results: Result[]
|
|
219
|
+
}
|
|
214
220
|
|
|
215
221
|
interface FixProblemsResponse {
|
|
216
222
|
id: string
|
|
@@ -225,6 +231,11 @@ const respond = (data: Response) => postMessage(data)
|
|
|
225
231
|
|
|
226
232
|
const findProblems = (data: FindProblemsArgs) => {
|
|
227
233
|
const { files, options = {} } = data
|
|
234
|
+
const idRespond = (results: Result[]) =>
|
|
235
|
+
respond({
|
|
236
|
+
id: data.id,
|
|
237
|
+
results,
|
|
238
|
+
})
|
|
228
239
|
const rules = RULES.filter(
|
|
229
240
|
(rule) =>
|
|
230
241
|
(!options.categories || options.categories.includes(rule.category)) &&
|
|
@@ -250,7 +261,7 @@ const findProblems = (data: FindProblemsArgs) => {
|
|
|
250
261
|
case 'per-file': {
|
|
251
262
|
if (fileType !== problem.path[0] || fileName !== problem.path[1]) {
|
|
252
263
|
if (batch.length > 0) {
|
|
253
|
-
|
|
264
|
+
idRespond(batch)
|
|
254
265
|
}
|
|
255
266
|
batch = []
|
|
256
267
|
fileType = problem.path[0]
|
|
@@ -264,7 +275,7 @@ const findProblems = (data: FindProblemsArgs) => {
|
|
|
264
275
|
default: {
|
|
265
276
|
batch.push(problem)
|
|
266
277
|
if (batch.length >= (options.batchSize ?? 1)) {
|
|
267
|
-
|
|
278
|
+
idRespond(batch)
|
|
268
279
|
batch = []
|
|
269
280
|
}
|
|
270
281
|
break
|
|
@@ -273,7 +284,7 @@ const findProblems = (data: FindProblemsArgs) => {
|
|
|
273
284
|
}
|
|
274
285
|
|
|
275
286
|
// Send the remaining results
|
|
276
|
-
|
|
287
|
+
idRespond(batch)
|
|
277
288
|
}
|
|
278
289
|
|
|
279
290
|
const fixProblems = (data: FixProblemsArgs) => {
|
|
@@ -0,0 +1,290 @@
|
|
|
1
|
+
import type { ProjectFiles } from '@nordcraft/ssr/dist/ssr.types'
|
|
2
|
+
import { describe, expect, test } from 'bun:test'
|
|
3
|
+
import { fixProject } from '../../fixProject'
|
|
4
|
+
import { searchProject } from '../../searchProject'
|
|
5
|
+
import { noStaticNodeCondition } from './noStaticNodeCondition'
|
|
6
|
+
|
|
7
|
+
describe('noStaticNodeCondition', () => {
|
|
8
|
+
test('should report node condition that is always truthy', () => {
|
|
9
|
+
const problems = Array.from(
|
|
10
|
+
searchProject({
|
|
11
|
+
files: {
|
|
12
|
+
components: {
|
|
13
|
+
test: {
|
|
14
|
+
name: 'test',
|
|
15
|
+
nodes: {
|
|
16
|
+
root: {
|
|
17
|
+
type: 'element',
|
|
18
|
+
attrs: {},
|
|
19
|
+
classes: {},
|
|
20
|
+
events: {},
|
|
21
|
+
tag: 'div',
|
|
22
|
+
children: [],
|
|
23
|
+
style: {},
|
|
24
|
+
condition: {
|
|
25
|
+
type: 'value',
|
|
26
|
+
value: true,
|
|
27
|
+
},
|
|
28
|
+
},
|
|
29
|
+
},
|
|
30
|
+
formulas: {},
|
|
31
|
+
apis: {},
|
|
32
|
+
attributes: {},
|
|
33
|
+
variables: {},
|
|
34
|
+
},
|
|
35
|
+
},
|
|
36
|
+
},
|
|
37
|
+
rules: [noStaticNodeCondition],
|
|
38
|
+
}),
|
|
39
|
+
)
|
|
40
|
+
|
|
41
|
+
expect(problems).toHaveLength(1)
|
|
42
|
+
expect(problems[0].code).toBe('no-static-node-condition')
|
|
43
|
+
expect(problems[0].details).toEqual({
|
|
44
|
+
result: true,
|
|
45
|
+
})
|
|
46
|
+
expect(problems[0].fixes).toEqual(['remove-condition'])
|
|
47
|
+
expect(problems[0].path).toEqual([
|
|
48
|
+
'components',
|
|
49
|
+
'test',
|
|
50
|
+
'nodes',
|
|
51
|
+
'root',
|
|
52
|
+
'condition',
|
|
53
|
+
])
|
|
54
|
+
})
|
|
55
|
+
|
|
56
|
+
test('should report node condition that is always falsy', () => {
|
|
57
|
+
const problems = Array.from(
|
|
58
|
+
searchProject({
|
|
59
|
+
files: {
|
|
60
|
+
components: {
|
|
61
|
+
test: {
|
|
62
|
+
name: 'test',
|
|
63
|
+
nodes: {
|
|
64
|
+
root: {
|
|
65
|
+
type: 'element',
|
|
66
|
+
attrs: {},
|
|
67
|
+
classes: {},
|
|
68
|
+
events: {},
|
|
69
|
+
tag: 'div',
|
|
70
|
+
children: [],
|
|
71
|
+
style: {},
|
|
72
|
+
condition: {
|
|
73
|
+
type: 'value',
|
|
74
|
+
value: false,
|
|
75
|
+
},
|
|
76
|
+
},
|
|
77
|
+
},
|
|
78
|
+
formulas: {},
|
|
79
|
+
apis: {},
|
|
80
|
+
attributes: {},
|
|
81
|
+
variables: {},
|
|
82
|
+
},
|
|
83
|
+
},
|
|
84
|
+
},
|
|
85
|
+
rules: [noStaticNodeCondition],
|
|
86
|
+
}),
|
|
87
|
+
)
|
|
88
|
+
|
|
89
|
+
expect(problems).toHaveLength(1)
|
|
90
|
+
expect(problems[0].code).toBe('no-static-node-condition')
|
|
91
|
+
expect(problems[0].details).toEqual({
|
|
92
|
+
result: false,
|
|
93
|
+
})
|
|
94
|
+
})
|
|
95
|
+
|
|
96
|
+
test('should not report node condition that is dynamic', () => {
|
|
97
|
+
const problems = Array.from(
|
|
98
|
+
searchProject({
|
|
99
|
+
files: {
|
|
100
|
+
components: {
|
|
101
|
+
test: {
|
|
102
|
+
name: 'test',
|
|
103
|
+
nodes: {
|
|
104
|
+
root: {
|
|
105
|
+
type: 'element',
|
|
106
|
+
attrs: {},
|
|
107
|
+
classes: {},
|
|
108
|
+
events: {},
|
|
109
|
+
tag: 'div',
|
|
110
|
+
children: [],
|
|
111
|
+
style: {},
|
|
112
|
+
condition: {
|
|
113
|
+
type: 'apply',
|
|
114
|
+
name: 'randomNumber',
|
|
115
|
+
arguments: [],
|
|
116
|
+
},
|
|
117
|
+
},
|
|
118
|
+
},
|
|
119
|
+
formulas: {},
|
|
120
|
+
apis: {},
|
|
121
|
+
attributes: {},
|
|
122
|
+
variables: {},
|
|
123
|
+
},
|
|
124
|
+
},
|
|
125
|
+
},
|
|
126
|
+
rules: [noStaticNodeCondition],
|
|
127
|
+
}),
|
|
128
|
+
)
|
|
129
|
+
|
|
130
|
+
expect(problems).toHaveLength(0)
|
|
131
|
+
})
|
|
132
|
+
|
|
133
|
+
test('should fix static truthy condition by removing the condition', () => {
|
|
134
|
+
const files: ProjectFiles = {
|
|
135
|
+
components: {
|
|
136
|
+
test: {
|
|
137
|
+
name: 'test',
|
|
138
|
+
nodes: {
|
|
139
|
+
root: {
|
|
140
|
+
type: 'element',
|
|
141
|
+
attrs: {},
|
|
142
|
+
classes: {},
|
|
143
|
+
events: {},
|
|
144
|
+
tag: 'div',
|
|
145
|
+
children: [],
|
|
146
|
+
style: {},
|
|
147
|
+
condition: {
|
|
148
|
+
type: 'value',
|
|
149
|
+
value: true,
|
|
150
|
+
},
|
|
151
|
+
},
|
|
152
|
+
},
|
|
153
|
+
formulas: {},
|
|
154
|
+
apis: {},
|
|
155
|
+
attributes: {},
|
|
156
|
+
variables: {},
|
|
157
|
+
},
|
|
158
|
+
},
|
|
159
|
+
}
|
|
160
|
+
const fixedFiles = fixProject({
|
|
161
|
+
files,
|
|
162
|
+
rule: noStaticNodeCondition,
|
|
163
|
+
fixType: 'remove-condition',
|
|
164
|
+
})
|
|
165
|
+
expect(fixedFiles).toMatchInlineSnapshot(`
|
|
166
|
+
{
|
|
167
|
+
"components": {
|
|
168
|
+
"test": {
|
|
169
|
+
"apis": {},
|
|
170
|
+
"attributes": {},
|
|
171
|
+
"formulas": {},
|
|
172
|
+
"name": "test",
|
|
173
|
+
"nodes": {
|
|
174
|
+
"root": {
|
|
175
|
+
"attrs": {},
|
|
176
|
+
"children": [],
|
|
177
|
+
"classes": {},
|
|
178
|
+
"events": {},
|
|
179
|
+
"style": {},
|
|
180
|
+
"tag": "div",
|
|
181
|
+
"type": "element",
|
|
182
|
+
},
|
|
183
|
+
},
|
|
184
|
+
"variables": {},
|
|
185
|
+
},
|
|
186
|
+
},
|
|
187
|
+
}
|
|
188
|
+
`)
|
|
189
|
+
})
|
|
190
|
+
|
|
191
|
+
test("should fix static falsy condition by removing the node and any parents' references to it", () => {
|
|
192
|
+
const files: ProjectFiles = {
|
|
193
|
+
components: {
|
|
194
|
+
test: {
|
|
195
|
+
name: 'test',
|
|
196
|
+
nodes: {
|
|
197
|
+
root: {
|
|
198
|
+
type: 'element',
|
|
199
|
+
attrs: {},
|
|
200
|
+
classes: {},
|
|
201
|
+
events: {},
|
|
202
|
+
tag: 'div',
|
|
203
|
+
children: ['alwaysHiddenElement', 'sometimesVisibleElement'],
|
|
204
|
+
style: {},
|
|
205
|
+
},
|
|
206
|
+
alwaysHiddenElement: {
|
|
207
|
+
type: 'element',
|
|
208
|
+
attrs: {},
|
|
209
|
+
classes: {},
|
|
210
|
+
events: {},
|
|
211
|
+
tag: 'div',
|
|
212
|
+
children: [],
|
|
213
|
+
style: {},
|
|
214
|
+
condition: {
|
|
215
|
+
type: 'value',
|
|
216
|
+
value: false,
|
|
217
|
+
},
|
|
218
|
+
},
|
|
219
|
+
sometimesVisibleElement: {
|
|
220
|
+
type: 'element',
|
|
221
|
+
attrs: {},
|
|
222
|
+
classes: {},
|
|
223
|
+
events: {},
|
|
224
|
+
tag: 'div',
|
|
225
|
+
children: [],
|
|
226
|
+
style: {},
|
|
227
|
+
condition: {
|
|
228
|
+
type: 'path',
|
|
229
|
+
path: ['Variables', 'maybe'],
|
|
230
|
+
},
|
|
231
|
+
},
|
|
232
|
+
},
|
|
233
|
+
formulas: {},
|
|
234
|
+
apis: {},
|
|
235
|
+
attributes: {},
|
|
236
|
+
variables: {},
|
|
237
|
+
},
|
|
238
|
+
},
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
const fixedFiles = fixProject({
|
|
242
|
+
files,
|
|
243
|
+
rule: noStaticNodeCondition,
|
|
244
|
+
fixType: 'remove-node',
|
|
245
|
+
})
|
|
246
|
+
|
|
247
|
+
expect(fixedFiles).toMatchInlineSnapshot(`
|
|
248
|
+
{
|
|
249
|
+
"components": {
|
|
250
|
+
"test": {
|
|
251
|
+
"apis": {},
|
|
252
|
+
"attributes": {},
|
|
253
|
+
"formulas": {},
|
|
254
|
+
"name": "test",
|
|
255
|
+
"nodes": {
|
|
256
|
+
"root": {
|
|
257
|
+
"attrs": {},
|
|
258
|
+
"children": [
|
|
259
|
+
"sometimesVisibleElement",
|
|
260
|
+
],
|
|
261
|
+
"classes": {},
|
|
262
|
+
"events": {},
|
|
263
|
+
"style": {},
|
|
264
|
+
"tag": "div",
|
|
265
|
+
"type": "element",
|
|
266
|
+
},
|
|
267
|
+
"sometimesVisibleElement": {
|
|
268
|
+
"attrs": {},
|
|
269
|
+
"children": [],
|
|
270
|
+
"classes": {},
|
|
271
|
+
"condition": {
|
|
272
|
+
"path": [
|
|
273
|
+
"Variables",
|
|
274
|
+
"maybe",
|
|
275
|
+
],
|
|
276
|
+
"type": "path",
|
|
277
|
+
},
|
|
278
|
+
"events": {},
|
|
279
|
+
"style": {},
|
|
280
|
+
"tag": "div",
|
|
281
|
+
"type": "element",
|
|
282
|
+
},
|
|
283
|
+
},
|
|
284
|
+
"variables": {},
|
|
285
|
+
},
|
|
286
|
+
},
|
|
287
|
+
}
|
|
288
|
+
`)
|
|
289
|
+
})
|
|
290
|
+
})
|