@putout/printer 18.1.8 → 18.2.1
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/ChangeLog +11 -0
- package/lib/tokenize/expressions/array-expression/array-expression.js +2 -2
- package/lib/tokenize/expressions/array-expression/before-if.js +2 -2
- package/lib/tokenize/expressions/array-expression/newline.js +10 -10
- package/lib/tokenize/expressions/function/class-method.js +3 -1
- package/lib/tokenize/expressions/function/function-declaration.js +3 -3
- package/lib/tokenize/expressions/object-expression/object-expression.js +7 -7
- package/lib/tokenize/is.js +1 -0
- package/lib/tokenize/statements/do-while-statement/do-while-statement.js +3 -1
- package/lib/tokenize/statements/export-declaration/export-default-declaration.js +3 -1
- package/lib/tokenize/statements/expression-statement/after-if.js +4 -4
- package/lib/tokenize/statements/expression-statement/expression-statement.js +5 -4
- package/lib/tokenize/statements/if-statement/if-statement.js +5 -3
- package/lib/tokenize/statements/switch-statement/switch-statement.js +3 -1
- package/lib/tokenize/statements/try-statement/try-statements.js +3 -1
- package/lib/tokenize/statements/variable-declaration/variable-declaration.js +3 -2
- package/lib/tokenize/type-checker/instrument.js +3 -1
- package/lib/tokenize/type-checker/type-checker.js +9 -21
- package/lib/tokenize/typescript/namespace/ts-module-declaration.js +3 -1
- package/lib/tokenize/typescript/ts-export-assignment/ts-export-assignment.js +3 -1
- package/package.json +1 -1
package/ChangeLog
CHANGED
|
@@ -1,3 +1,14 @@
|
|
|
1
|
+
2026.03.07, v18.2.1
|
|
2
|
+
|
|
3
|
+
fix:
|
|
4
|
+
- b4e4b01 @putout/printer: ExpressionStatement
|
|
5
|
+
|
|
6
|
+
2026.03.07, v18.2.0
|
|
7
|
+
|
|
8
|
+
feature:
|
|
9
|
+
- 87135c0 @putout/printer: type-checker: disable instrument: add support
|
|
10
|
+
- 29e0a3c @putout/printer: type-checker: rm deepness
|
|
11
|
+
|
|
1
12
|
2026.03.07, v18.1.8
|
|
2
13
|
|
|
3
14
|
feature:
|
|
@@ -71,8 +71,8 @@ const isSimpleBetweenObjects = createTypeChecker([
|
|
|
71
71
|
]);
|
|
72
72
|
|
|
73
73
|
const isSpaceAfterComa = createTypeChecker([
|
|
74
|
-
callWithNext(isSimpleBetweenObjects),
|
|
75
|
-
'+: -> !ObjectExpression',
|
|
74
|
+
['+', callWithNext(isSimpleBetweenObjects)],
|
|
75
|
+
['+: -> !ObjectExpression'],
|
|
76
76
|
]);
|
|
77
77
|
|
|
78
78
|
export const ArrayExpression = {
|
|
@@ -19,6 +19,6 @@ const isStringAndIdentifierInsideOneElementArray = createTypeChecker([
|
|
|
19
19
|
export const beforeIf = createTypeChecker([
|
|
20
20
|
['-: -> !', isInsideArray],
|
|
21
21
|
['-: parentPath ->', isCoupleLines],
|
|
22
|
-
isIdentifierAndIdentifier,
|
|
23
|
-
isStringAndIdentifierInsideOneElementArray,
|
|
22
|
+
['+', isIdentifierAndIdentifier],
|
|
23
|
+
['+', isStringAndIdentifierInsideOneElementArray],
|
|
24
24
|
]);
|
|
@@ -30,7 +30,7 @@ const isStringAndString = (path) => {
|
|
|
30
30
|
const isStringsInsideArray = createTypeChecker([
|
|
31
31
|
['-: -> !', isStringAndString],
|
|
32
32
|
['-: -> !', isInsideArray],
|
|
33
|
-
'+: parentPath.node.elements.0 -> ArrayExpression',
|
|
33
|
+
['+: parentPath.node.elements.0 -> ArrayExpression'],
|
|
34
34
|
]);
|
|
35
35
|
|
|
36
36
|
const isTwoSimplesInsideObjectProperty = (path) => {
|
|
@@ -183,13 +183,13 @@ const isElementsMoreThenThree = (path) => {
|
|
|
183
183
|
};
|
|
184
184
|
|
|
185
185
|
const isElementsMoreThenThreeWithNotFirstObject = createTypeChecker([
|
|
186
|
-
'-: node.elements.0 -> ObjectExpression',
|
|
187
|
-
isElementsMoreThenThree,
|
|
186
|
+
['-: node.elements.0 -> ObjectExpression'],
|
|
187
|
+
['+', isElementsMoreThenThree],
|
|
188
188
|
]);
|
|
189
189
|
|
|
190
190
|
const isElementsMoreThenMaxWithFirstString = createTypeChecker([
|
|
191
|
-
'-: node.elements.0 -> !StringLiteral',
|
|
192
|
-
isElementsMoreThenMax,
|
|
191
|
+
['-: node.elements.0 -> !StringLiteral'],
|
|
192
|
+
['+', isElementsMoreThenMax],
|
|
193
193
|
]);
|
|
194
194
|
|
|
195
195
|
const isOne = (a) => a === 1;
|
|
@@ -204,8 +204,8 @@ export const isMultiLine = createTypeChecker([
|
|
|
204
204
|
['+', isBodyWithOneElement],
|
|
205
205
|
['+', isMoreThenMaxElementLengthInOneLine],
|
|
206
206
|
['+', isElementsMoreThenMaxWithFirstString],
|
|
207
|
-
isElementsMoreThenThreeWithNotFirstObject,
|
|
208
|
-
isSimpleAndNotEmptyObject,
|
|
207
|
+
['+', isElementsMoreThenThreeWithNotFirstObject],
|
|
208
|
+
['+', isSimpleAndNotEmptyObject],
|
|
209
209
|
['-', isOneSimple],
|
|
210
210
|
['-', isOneSpread],
|
|
211
211
|
['-', isIdentifierAndIdentifier],
|
|
@@ -225,8 +225,8 @@ export const isMultiLine = createTypeChecker([
|
|
|
225
225
|
['-', isSimpleAndObject],
|
|
226
226
|
['-', isSiblingIsArray],
|
|
227
227
|
['-', isStringsInsideArray],
|
|
228
|
-
tooLong,
|
|
229
|
-
isCoupleLines,
|
|
228
|
+
['+', tooLong],
|
|
229
|
+
['+', isCoupleLines],
|
|
230
230
|
['-', isNumbersArray],
|
|
231
231
|
]);
|
|
232
232
|
|
|
@@ -328,7 +328,7 @@ export function isIncreaseIndent(path) {
|
|
|
328
328
|
|
|
329
329
|
const isInsideCallLoop = createTypeChecker([
|
|
330
330
|
['-: -> !', isInsideCall],
|
|
331
|
-
'+: parentPath.parentPath -> ForOfStatement',
|
|
331
|
+
['+: parentPath.parentPath -> ForOfStatement'],
|
|
332
332
|
]);
|
|
333
333
|
|
|
334
334
|
const isStringAndObject = (elements) => {
|
|
@@ -23,13 +23,13 @@ const isIndentAfter = createTypeChecker([
|
|
|
23
23
|
]);
|
|
24
24
|
|
|
25
25
|
const isNotInsideExportDefaultWithBody = createTypeChecker([
|
|
26
|
-
'+: parentPath -> !ExportDefaultDeclaration',
|
|
26
|
+
['+: parentPath -> !ExportDefaultDeclaration'],
|
|
27
27
|
['+: -> !', hasFnBody],
|
|
28
28
|
]);
|
|
29
29
|
|
|
30
30
|
const isInsideBlockLike = createTypeChecker([
|
|
31
|
-
'+: parentPath.parentPath -> TSModuleBlock',
|
|
32
|
-
'-: parentPath -> !BlockStatement',
|
|
31
|
+
['+: parentPath.parentPath -> TSModuleBlock'],
|
|
32
|
+
['-: parentPath -> !BlockStatement'],
|
|
33
33
|
['+: -> !', hasFnBody],
|
|
34
34
|
]);
|
|
35
35
|
|
|
@@ -44,27 +44,27 @@ const isParens = createTypeChecker([isInsideBody, isInsideExpression]);
|
|
|
44
44
|
const getCallee = (fn) => (a) => fn(a.get('callee'));
|
|
45
45
|
|
|
46
46
|
const isMemberExpressionCallee = createTypeChecker([
|
|
47
|
-
'-: parentPath -> !CallExpression',
|
|
47
|
+
['-: parentPath -> !CallExpression'],
|
|
48
48
|
['-: parentPath -> !', getCallee(isMemberExpression)],
|
|
49
49
|
['+: parentPath', getCallee(isLooksLikeChain)],
|
|
50
50
|
]);
|
|
51
51
|
|
|
52
52
|
const isInsideNestedArrayCall = createTypeChecker([
|
|
53
|
-
isInsideTuple,
|
|
54
|
-
'-: parentPath -> !ArrayExpression',
|
|
55
|
-
'-: parentPath.parentPath -> !ArrayExpression',
|
|
53
|
+
['+', isInsideTuple],
|
|
54
|
+
['-: parentPath -> !ArrayExpression'],
|
|
55
|
+
['-: parentPath.parentPath -> !ArrayExpression'],
|
|
56
56
|
['+: parentPath.parentPath', isInsideCall],
|
|
57
57
|
]);
|
|
58
58
|
|
|
59
59
|
const isInsideTupleLike = createTypeChecker([
|
|
60
60
|
['+', isInsideTuple],
|
|
61
|
-
'+: parentPath.parentPath.node.elements.0 -> StringLiteral',
|
|
61
|
+
['+: parentPath.parentPath.node.elements.0 -> StringLiteral'],
|
|
62
62
|
]);
|
|
63
63
|
|
|
64
64
|
export const isManyLines = createTypeChecker([
|
|
65
65
|
['-', hasNoProperties],
|
|
66
|
-
'-: parentPath -> ForOfStatement',
|
|
67
|
-
'+: node.properties.0 -> SpreadElement',
|
|
66
|
+
['-: parentPath -> ForOfStatement'],
|
|
67
|
+
['+: node.properties.0 -> SpreadElement'],
|
|
68
68
|
['-', notLastArgInsideCall],
|
|
69
69
|
['-', isForOf],
|
|
70
70
|
['-', isIf],
|
package/lib/tokenize/is.js
CHANGED
|
@@ -31,6 +31,7 @@ export const isInsideTSModuleBlock = ({parentPath}) => isTSModuleBlock(parentPat
|
|
|
31
31
|
export const isInsideCall = ({parentPath}) => parentPath.isCallExpression();
|
|
32
32
|
export const isInsideReturn = ({parentPath}) => parentPath.isReturnStatement();
|
|
33
33
|
export const callWithNext = (fn) => (path) => fn(path.getNextSibling());
|
|
34
|
+
export const callWithParent = (fn) => (path) => fn(path.parentPath);
|
|
34
35
|
|
|
35
36
|
export const isNext = (path) => {
|
|
36
37
|
const next = path.getNextSibling();
|
|
@@ -20,7 +20,9 @@ export const ExportDefaultDeclaration = {
|
|
|
20
20
|
traverse(declaration);
|
|
21
21
|
maybe.print(shouldAddSemicolon(declaration), ';');
|
|
22
22
|
},
|
|
23
|
-
afterSatisfy: () => [
|
|
23
|
+
afterSatisfy: () => [
|
|
24
|
+
isNext,
|
|
25
|
+
],
|
|
24
26
|
after(path, {print, maybe}) {
|
|
25
27
|
print.newline();
|
|
26
28
|
maybe.print.newline(!isVarAfterFn(path));
|
|
@@ -16,9 +16,9 @@ function isNotLastOrParentLast(path) {
|
|
|
16
16
|
const isNextUp = (path) => path.findParent(isNext);
|
|
17
17
|
|
|
18
18
|
const isTopParentLast = createTypeChecker([
|
|
19
|
-
'-: parentPath -> !IfStatement',
|
|
20
|
-
'-: parentPath.parentPath -> !IfStatement',
|
|
21
|
-
'-: parentPath.parentPath.parentPath -> !IfStatement',
|
|
19
|
+
['-: parentPath -> !IfStatement'],
|
|
20
|
+
['-: parentPath.parentPath -> !IfStatement'],
|
|
21
|
+
['-: parentPath.parentPath.parentPath -> !IfStatement'],
|
|
22
22
|
['+: parentPath.parentPath.parentPath', isLast],
|
|
23
23
|
]);
|
|
24
24
|
|
|
@@ -32,7 +32,7 @@ const satisfyAfter = satisfy([
|
|
|
32
32
|
const isPathIsConsequent = ({node, parentPath}) => node !== parentPath.node.consequent;
|
|
33
33
|
|
|
34
34
|
const isBeforeElse = createTypeChecker([
|
|
35
|
-
'-: parentPath -> !IfStatement',
|
|
35
|
+
['-: parentPath -> !IfStatement'],
|
|
36
36
|
['-:', isPathIsConsequent],
|
|
37
37
|
['+: parentPath.node.alternate', Boolean],
|
|
38
38
|
]);
|
|
@@ -26,7 +26,7 @@ const isCallInsideExpression = createTypeChecker([
|
|
|
26
26
|
]);
|
|
27
27
|
|
|
28
28
|
const isNextToAssignmentCall = createTypeChecker([
|
|
29
|
-
'-: node.expression -> AssignmentExpression',
|
|
29
|
+
['-: node.expression -> AssignmentExpression'],
|
|
30
30
|
['+', callWithNext(isCallInsideExpression)],
|
|
31
31
|
]);
|
|
32
32
|
|
|
@@ -43,8 +43,8 @@ const isNextStatementWithBlockComment = createTypeChecker([
|
|
|
43
43
|
]);
|
|
44
44
|
|
|
45
45
|
const isBreakline = createTypeChecker([
|
|
46
|
-
isNewlineBetweenSiblings,
|
|
47
|
-
callWithNext(isIfStatement),
|
|
46
|
+
['+', isNewlineBetweenSiblings],
|
|
47
|
+
['+', callWithNext(isIfStatement)],
|
|
48
48
|
]);
|
|
49
49
|
|
|
50
50
|
const isIndent = createTypeChecker([
|
|
@@ -54,7 +54,7 @@ const isIndent = createTypeChecker([
|
|
|
54
54
|
]);
|
|
55
55
|
|
|
56
56
|
export const isIndentAfter = createTypeChecker([
|
|
57
|
-
'-: node.expression -> !AssignmentExpression',
|
|
57
|
+
['-: node.expression -> !AssignmentExpression'],
|
|
58
58
|
['+', callWithNext(hasLeadingComment)],
|
|
59
59
|
]);
|
|
60
60
|
|
|
@@ -90,3 +90,4 @@ export const ExpressionStatement = {
|
|
|
90
90
|
maybe.markAfter(store(), path);
|
|
91
91
|
},
|
|
92
92
|
};
|
|
93
|
+
|
|
@@ -36,7 +36,7 @@ const isStatementNotExpression = (path) => {
|
|
|
36
36
|
|
|
37
37
|
const isInsideNestedBody = createTypeChecker([
|
|
38
38
|
['-: -> !', isInsideBlock],
|
|
39
|
-
'+: parentPath.parentPath -> BlockStatement',
|
|
39
|
+
['+: parentPath.parentPath -> BlockStatement'],
|
|
40
40
|
]);
|
|
41
41
|
|
|
42
42
|
const isTopLevel = ({parentPath}) => parentPath.parentPath.isProgram();
|
|
@@ -48,7 +48,7 @@ const isLastEmptyInsideBody = createTypeChecker([
|
|
|
48
48
|
['-: -> !', isInsideBlock],
|
|
49
49
|
['-: -> !', isBlockConsequent],
|
|
50
50
|
['-', isConsequentHasBody],
|
|
51
|
-
'+: parentPath.parentPath -> FunctionDeclaration',
|
|
51
|
+
['+: parentPath.parentPath -> FunctionDeclaration'],
|
|
52
52
|
]);
|
|
53
53
|
|
|
54
54
|
export const IfStatement = {
|
|
@@ -125,7 +125,9 @@ export const IfStatement = {
|
|
|
125
125
|
if (isLastEmptyInsideBody(path))
|
|
126
126
|
print.newline();
|
|
127
127
|
},
|
|
128
|
-
afterSatisfy: () => [
|
|
128
|
+
afterSatisfy: () => [
|
|
129
|
+
isNext,
|
|
130
|
+
],
|
|
129
131
|
after: (path, {print}) => {
|
|
130
132
|
print.linebreak();
|
|
131
133
|
markAfter(path);
|
|
@@ -14,6 +14,7 @@ import {
|
|
|
14
14
|
isInsideProgram,
|
|
15
15
|
isInsideSwitchCase,
|
|
16
16
|
isInsideBody,
|
|
17
|
+
callWithParent,
|
|
17
18
|
} from '#is';
|
|
18
19
|
import {maybeSpaceAfterKeyword} from './maybe-space-after-keyword.js';
|
|
19
20
|
import {isConcatenation} from '../../expressions/binary-expression/concatenate.js';
|
|
@@ -36,12 +37,12 @@ const isParentTSModuleBlock = (path) => path.parentPath.isTSModuleBlock();
|
|
|
36
37
|
const isParentSwitchCase = (path) => path.parentPath.isSwitchCase();
|
|
37
38
|
const isFirstInSwitch = (path) => path.parentPath.get('consequent.0') === path;
|
|
38
39
|
|
|
39
|
-
const isInsideParentLike = createTypeChecker(
|
|
40
|
+
const isInsideParentLike = callWithParent(createTypeChecker([
|
|
40
41
|
'Program',
|
|
41
42
|
'BlockStatement',
|
|
42
43
|
'ExportNamedDeclaration',
|
|
43
44
|
'LabeledStatement',
|
|
44
|
-
]);
|
|
45
|
+
]));
|
|
45
46
|
|
|
46
47
|
const isNeedSemicolon = createTypeChecker([
|
|
47
48
|
isInsideParentLike,
|
|
@@ -10,12 +10,13 @@ export const instrument = (typeNames, fn, overrides = {}) => {
|
|
|
10
10
|
const {
|
|
11
11
|
env = _env,
|
|
12
12
|
coverage = Coverage,
|
|
13
|
+
instrument = true,
|
|
13
14
|
} = overrides;
|
|
14
15
|
|
|
15
16
|
const {length} = typeNames;
|
|
16
17
|
const error = Error();
|
|
17
18
|
const location = parseCallLocation(error);
|
|
18
|
-
const on = env.TYPE_CHECK;
|
|
19
|
+
const on = instrument && env.TYPE_CHECK;
|
|
19
20
|
const covered = new Set();
|
|
20
21
|
|
|
21
22
|
if (on && !location.includes('type-checker.spec.js'))
|
|
@@ -36,3 +37,4 @@ export const instrument = (typeNames, fn, overrides = {}) => {
|
|
|
36
37
|
};
|
|
37
38
|
|
|
38
39
|
export const getCoverage = () => Coverage;
|
|
40
|
+
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import {jessy} from 'jessy';
|
|
2
|
-
import {instrument} from '#type-checker/instrument';
|
|
2
|
+
import {instrument as _instrument} from '#type-checker/instrument';
|
|
3
3
|
import {parseOperation, parseTypeNames} from './parsers.js';
|
|
4
4
|
import {equal, maybeCall} from './comparators.js';
|
|
5
5
|
|
|
@@ -8,26 +8,12 @@ const SKIP = [
|
|
|
8
8
|
false,
|
|
9
9
|
];
|
|
10
10
|
|
|
11
|
-
export const createTypeChecker = (
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
}
|
|
16
|
-
|
|
11
|
+
export const createTypeChecker = (typeNames, overrides = {}) => {
|
|
12
|
+
const {
|
|
13
|
+
instrumentCoverage = _instrument,
|
|
14
|
+
} = overrides;
|
|
17
15
|
const tuples = parseTypeNames(typeNames);
|
|
18
|
-
|
|
19
|
-
return instrument(typeNames, (path, options) => {
|
|
20
|
-
let i = deepness.split('.').length;
|
|
21
|
-
|
|
22
|
-
while (--i)
|
|
23
|
-
path = path?.parentPath;
|
|
24
|
-
|
|
25
|
-
if (!path)
|
|
26
|
-
return [
|
|
27
|
-
Infinity,
|
|
28
|
-
false,
|
|
29
|
-
];
|
|
30
|
-
|
|
16
|
+
const typeChecker = (path, options) => {
|
|
31
17
|
for (const [index, [operation, typeName]] of tuples.entries()) {
|
|
32
18
|
const [result, selector, not] = parseOperation(operation);
|
|
33
19
|
let currentPath = path;
|
|
@@ -48,5 +34,7 @@ export const createTypeChecker = (deepness, typeNames) => {
|
|
|
48
34
|
}
|
|
49
35
|
|
|
50
36
|
return SKIP;
|
|
51
|
-
}
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
return instrumentCoverage(typeNames, typeChecker, overrides);
|
|
52
40
|
};
|
package/package.json
CHANGED