Skip to content

Commit aa5838c

Browse files
committed
add code fix
1 parent d00f2b5 commit aa5838c

File tree

6 files changed

+93
-7
lines changed

6 files changed

+93
-7
lines changed

src/compiler/diagnosticMessages.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5645,6 +5645,10 @@
56455645
"category": "Message",
56465646
"code": 95116
56475647
},
5648+
"Remove parentheses": {
5649+
"category": "Message",
5650+
"code": 95117
5651+
},
56485652

56495653
"No value exists in scope for the shorthand property '{0}'. Either declare one or provide an initializer.": {
56505654
"category": "Error",

src/compiler/parser.ts

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4897,7 +4897,10 @@ namespace ts {
48974897
callExpr.expression = expression;
48984898
callExpr.questionDotToken = questionDotToken;
48994899
callExpr.typeArguments = typeArguments;
4900-
callExpr.arguments = parseArgumentList();
4900+
const { openParen, argumentList, closeParen } = parseArgumentList();
4901+
callExpr.openParenToken = openParen;
4902+
callExpr.closeParenToken = closeParen;
4903+
callExpr.arguments = argumentList;
49014904
if (questionDotToken || tryReparseOptionalChain(expression)) {
49024905
callExpr.flags |= NodeFlags.OptionalChain;
49034906
}
@@ -4909,7 +4912,10 @@ namespace ts {
49094912
const callExpr = <CallExpression>createNode(SyntaxKind.CallExpression, expression.pos);
49104913
callExpr.expression = expression;
49114914
callExpr.questionDotToken = questionDotToken;
4912-
callExpr.arguments = parseArgumentList();
4915+
const { openParen, argumentList, closeParen } = parseArgumentList();
4916+
callExpr.openParenToken = openParen;
4917+
callExpr.closeParenToken = closeParen;
4918+
callExpr.arguments = argumentList;
49134919
if (questionDotToken || tryReparseOptionalChain(expression)) {
49144920
callExpr.flags |= NodeFlags.OptionalChain;
49154921
}
@@ -4931,10 +4937,10 @@ namespace ts {
49314937
}
49324938

49334939
function parseArgumentList() {
4934-
parseExpected(SyntaxKind.OpenParenToken);
4935-
const result = parseDelimitedList(ParsingContext.ArgumentExpressions, parseArgumentExpression);
4936-
parseExpected(SyntaxKind.CloseParenToken);
4937-
return result;
4940+
const openParen = parseExpectedToken(SyntaxKind.OpenParenToken);
4941+
const argumentList = parseDelimitedList(ParsingContext.ArgumentExpressions, parseArgumentExpression);
4942+
const closeParen = parseExpectedToken(SyntaxKind.CloseParenToken);
4943+
return { openParen, argumentList, closeParen };
49384944
}
49394945

49404946
function parseTypeArgumentsInExpression() {
@@ -5221,7 +5227,10 @@ namespace ts {
52215227
node.expression = expression;
52225228
node.typeArguments = typeArguments;
52235229
if (token() === SyntaxKind.OpenParenToken) {
5224-
node.arguments = parseArgumentList();
5230+
const { openParen, argumentList, closeParen } = parseArgumentList();
5231+
node.openParenToken = openParen;
5232+
node.closeParenToken = closeParen;
5233+
node.arguments = argumentList;
52255234
}
52265235
else if (node.typeArguments) {
52275236
parseErrorAt(fullStart, scanner.getStartPos(), Diagnostics.A_new_expression_with_type_arguments_must_always_be_followed_by_a_parenthesized_argument_list);

src/compiler/types.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -769,6 +769,8 @@ namespace ts {
769769
export type PlusToken = Token<SyntaxKind.PlusToken>;
770770
export type MinusToken = Token<SyntaxKind.MinusToken>;
771771
export type AssertsToken = Token<SyntaxKind.AssertsKeyword>;
772+
export type OpenParenToken = Token<SyntaxKind.OpenParenToken>;
773+
export type CloseParenToken = Token<SyntaxKind.CloseParenToken>;
772774

773775
export type Modifier
774776
= Token<SyntaxKind.AbstractKeyword>
@@ -1917,6 +1919,8 @@ namespace ts {
19171919
expression: LeftHandSideExpression;
19181920
questionDotToken?: QuestionDotToken;
19191921
typeArguments?: NodeArray<TypeNode>;
1922+
openParenToken: OpenParenToken;
1923+
closeParenToken: CloseParenToken;
19201924
arguments: NodeArray<Expression>;
19211925
}
19221926

@@ -1997,6 +2001,8 @@ namespace ts {
19972001
expression: LeftHandSideExpression;
19982002
typeArguments?: NodeArray<TypeNode>;
19992003
arguments?: NodeArray<Expression>;
2004+
openParenToken?: OpenParenToken;
2005+
closeParenToken?: CloseParenToken;
20002006
}
20012007

20022008
export interface TaggedTemplateExpression extends MemberExpression {
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
/* @internal */
2+
namespace ts.codefix {
3+
const fixId = "removeAccidentalCallParentheses";
4+
const errorCodes = [
5+
Diagnostics.This_expression_is_not_callable_because_it_is_a_get_accessor_Did_you_mean_to_use_it_without.code,
6+
];
7+
registerCodeFix({
8+
errorCodes,
9+
getCodeActions(context) {
10+
let token = getTokenAtPosition(context.sourceFile, context.span.start);
11+
while (token && !isCallExpression(token)) {
12+
token = token.parent;
13+
}
14+
if (!token) {
15+
return undefined;
16+
}
17+
const callExpression = token;
18+
const changes = textChanges.ChangeTracker.with(context, t => {
19+
t.deleteNodeRange(context.sourceFile, callExpression.openParenToken, callExpression.closeParenToken);
20+
});
21+
return [createCodeFixActionWithoutFixAll(fixId, changes, Diagnostics.Remove_parentheses)];
22+
},
23+
fixIds: [fixId],
24+
});
25+
}

src/services/tsconfig.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,7 @@
9494
"codefixes/useBigintLiteral.ts",
9595
"codefixes/fixAddModuleReferTypeMissingTypeof.ts",
9696
"codefixes/convertToMappedObjectType.ts",
97+
"codefixes/removeAccidentalCallParentheses.ts",
9798
"codefixes/removeUnnecessaryAwait.ts",
9899
"codefixes/splitTypeOnlyImport.ts",
99100
"codefixes/convertConstToLet.ts",
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
/// <reference path='fourslash.ts' />
2+
3+
//// class Test24554 {
4+
//// get property(): number { return 1; }
5+
//// }
6+
//// function test24554(x: Test24554) {
7+
//// return x.property();
8+
//// }
9+
//// function test_2(x: { y: Test24554 }) {
10+
//// return x.y.property ( /* bye */ );
11+
//// }
12+
13+
verify.codeFix({
14+
description: "Remove parentheses",
15+
index: 0,
16+
newFileContent:
17+
`class Test24554 {
18+
get property(): number { return 1; }
19+
}
20+
function test24554(x: Test24554) {
21+
return x.property;
22+
}
23+
function test_2(x: { y: Test24554 }) {
24+
return x.y.property ( /* bye */ );
25+
}`
26+
});
27+
28+
verify.codeFix({
29+
description: "Remove parentheses",
30+
index: 1,
31+
newFileContent:
32+
`class Test24554 {
33+
get property(): number { return 1; }
34+
}
35+
function test24554(x: Test24554) {
36+
return x.property();
37+
}
38+
function test_2(x: { y: Test24554 }) {
39+
return x.y.property;
40+
}`
41+
});

0 commit comments

Comments
 (0)