mirror of
https://github.com/microsoft/TypeScript.git
synced 2025-11-18 17:21:48 +00:00
Improve error spans on chained method calls
This commit is contained in:
+15
-5
@@ -21223,7 +21223,8 @@ namespace ts {
|
||||
reorderCandidates(signatures, candidates);
|
||||
if (!candidates.length) {
|
||||
if (reportErrors) {
|
||||
diagnostics.add(createDiagnosticForNode(node, Diagnostics.Call_target_does_not_contain_any_signatures));
|
||||
const errorNode = getCallErrorNode(node);
|
||||
diagnostics.add(createDiagnosticForNode(errorNode, Diagnostics.Call_target_does_not_contain_any_signatures));
|
||||
}
|
||||
return resolveErrorCall(node);
|
||||
}
|
||||
@@ -21301,11 +21302,13 @@ namespace ts {
|
||||
// If candidate is undefined, it means that no candidates had a suitable arity. In that case,
|
||||
// skip the checkApplicableSignature check.
|
||||
if (reportErrors) {
|
||||
const errorNode = getCallErrorNode(node);
|
||||
|
||||
if (candidateForArgumentError) {
|
||||
checkApplicableSignature(node, args, candidateForArgumentError, assignableRelation, CheckMode.Normal, /*reportErrors*/ true);
|
||||
}
|
||||
else if (candidateForArgumentArityError) {
|
||||
diagnostics.add(getArgumentArityError(node, [candidateForArgumentArityError], args));
|
||||
diagnostics.add(getArgumentArityError(errorNode, [candidateForArgumentArityError], args));
|
||||
}
|
||||
else if (candidateForTypeArgumentError) {
|
||||
checkTypeArguments(candidateForTypeArgumentError, (node as CallExpression | TaggedTemplateExpression | JsxOpeningLikeElement).typeArguments!, /*reportErrors*/ true, fallbackError);
|
||||
@@ -21313,19 +21316,26 @@ namespace ts {
|
||||
else {
|
||||
const signaturesWithCorrectTypeArgumentArity = filter(signatures, s => hasCorrectTypeArgumentArity(s, typeArguments));
|
||||
if (signaturesWithCorrectTypeArgumentArity.length === 0) {
|
||||
diagnostics.add(getTypeArgumentArityError(node, signatures, typeArguments!));
|
||||
diagnostics.add(getTypeArgumentArityError(errorNode, signatures, typeArguments!));
|
||||
}
|
||||
else if (!isDecorator) {
|
||||
diagnostics.add(getArgumentArityError(node, signaturesWithCorrectTypeArgumentArity, args));
|
||||
diagnostics.add(getArgumentArityError(errorNode, signaturesWithCorrectTypeArgumentArity, args));
|
||||
}
|
||||
else if (fallbackError) {
|
||||
diagnostics.add(createDiagnosticForNode(node, fallbackError));
|
||||
diagnostics.add(createDiagnosticForNode(errorNode, fallbackError));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return produceDiagnostics || !args ? resolveErrorCall(node) : getCandidateForOverloadFailure(node, candidates, args, !!candidatesOutArray);
|
||||
|
||||
function getCallErrorNode(node: CallLikeExpression): Node {
|
||||
if (isCallExpression(node) && isPropertyAccessExpression(node.expression)) {
|
||||
return node.expression.name;
|
||||
}
|
||||
return node;
|
||||
}
|
||||
|
||||
function chooseOverload(candidates: Signature[], relation: Map<RelationComparisonResult>, signatureHelpTrailingComma = false) {
|
||||
candidateForArgumentError = undefined;
|
||||
candidateForArgumentArityError = undefined;
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
tests/cases/compiler/methodChainError.ts(9,6): error TS2554: Expected 1 arguments, but got 0.
|
||||
|
||||
|
||||
==== tests/cases/compiler/methodChainError.ts (1 errors) ====
|
||||
class Builder {
|
||||
method(param: string): Builder {
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
new Builder()
|
||||
.method("a")
|
||||
.method();
|
||||
~~~~~~
|
||||
!!! error TS2554: Expected 1 arguments, but got 0.
|
||||
!!! related TS6210 tests/cases/compiler/methodChainError.ts:2:12: An argument for 'param' was not provided.
|
||||
@@ -0,0 +1,23 @@
|
||||
//// [methodChainError.ts]
|
||||
class Builder {
|
||||
method(param: string): Builder {
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
new Builder()
|
||||
.method("a")
|
||||
.method();
|
||||
|
||||
//// [methodChainError.js]
|
||||
var Builder = /** @class */ (function () {
|
||||
function Builder() {
|
||||
}
|
||||
Builder.prototype.method = function (param) {
|
||||
return this;
|
||||
};
|
||||
return Builder;
|
||||
}());
|
||||
new Builder()
|
||||
.method("a")
|
||||
.method();
|
||||
@@ -0,0 +1,25 @@
|
||||
=== tests/cases/compiler/methodChainError.ts ===
|
||||
class Builder {
|
||||
>Builder : Symbol(Builder, Decl(methodChainError.ts, 0, 0))
|
||||
|
||||
method(param: string): Builder {
|
||||
>method : Symbol(Builder.method, Decl(methodChainError.ts, 0, 15))
|
||||
>param : Symbol(param, Decl(methodChainError.ts, 1, 11))
|
||||
>Builder : Symbol(Builder, Decl(methodChainError.ts, 0, 0))
|
||||
|
||||
return this;
|
||||
>this : Symbol(Builder, Decl(methodChainError.ts, 0, 0))
|
||||
}
|
||||
}
|
||||
|
||||
new Builder()
|
||||
>new Builder() .method("a") .method : Symbol(Builder.method, Decl(methodChainError.ts, 0, 15))
|
||||
>new Builder() .method : Symbol(Builder.method, Decl(methodChainError.ts, 0, 15))
|
||||
>Builder : Symbol(Builder, Decl(methodChainError.ts, 0, 0))
|
||||
|
||||
.method("a")
|
||||
>method : Symbol(Builder.method, Decl(methodChainError.ts, 0, 15))
|
||||
|
||||
.method();
|
||||
>method : Symbol(Builder.method, Decl(methodChainError.ts, 0, 15))
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
=== tests/cases/compiler/methodChainError.ts ===
|
||||
class Builder {
|
||||
>Builder : Builder
|
||||
|
||||
method(param: string): Builder {
|
||||
>method : (param: string) => Builder
|
||||
>param : string
|
||||
|
||||
return this;
|
||||
>this : this
|
||||
}
|
||||
}
|
||||
|
||||
new Builder()
|
||||
>new Builder() .method("a") .method() : Builder
|
||||
>new Builder() .method("a") .method : (param: string) => Builder
|
||||
>new Builder() .method("a") : Builder
|
||||
>new Builder() .method : (param: string) => Builder
|
||||
>new Builder() : Builder
|
||||
>Builder : typeof Builder
|
||||
|
||||
.method("a")
|
||||
>method : (param: string) => Builder
|
||||
>"a" : "a"
|
||||
|
||||
.method();
|
||||
>method : (param: string) => Builder
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
class Builder {
|
||||
method(param: string): Builder {
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
new Builder()
|
||||
.method("a")
|
||||
.method();
|
||||
Reference in New Issue
Block a user