mirror of
https://github.com/microsoft/TypeScript.git
synced 2025-11-18 17:21:48 +00:00
Merge branch 'master' into release-3.0
This commit is contained in:
+51
-46
@@ -18215,7 +18215,6 @@ namespace ts {
|
||||
|
||||
function hasCorrectArity(node: CallLikeExpression, args: ReadonlyArray<Expression>, signature: Signature, signatureHelpTrailingComma = false) {
|
||||
let argCount: number; // Apparent number of arguments we will have in this call
|
||||
let typeArguments: NodeArray<TypeNode> | undefined; // Type arguments (undefined if none)
|
||||
let callIsIncomplete = false; // In incomplete call we want to be lenient when we have too few arguments
|
||||
let spreadArgIndex = -1;
|
||||
|
||||
@@ -18228,7 +18227,6 @@ namespace ts {
|
||||
// Even if the call is incomplete, we'll have a missing expression as our last argument,
|
||||
// so we can say the count is just the arg list length
|
||||
argCount = args.length;
|
||||
typeArguments = node.typeArguments;
|
||||
|
||||
if (node.template.kind === SyntaxKind.TemplateExpression) {
|
||||
// If a tagged template expression lacks a tail literal, the call is incomplete.
|
||||
@@ -18246,7 +18244,6 @@ namespace ts {
|
||||
}
|
||||
}
|
||||
else if (node.kind === SyntaxKind.Decorator) {
|
||||
typeArguments = undefined;
|
||||
argCount = getEffectiveArgumentCount(node, /*args*/ undefined!, signature);
|
||||
}
|
||||
else {
|
||||
@@ -18261,14 +18258,9 @@ namespace ts {
|
||||
// If we are missing the close parenthesis, the call is incomplete.
|
||||
callIsIncomplete = node.arguments.end === node.end;
|
||||
|
||||
typeArguments = node.typeArguments;
|
||||
spreadArgIndex = getSpreadArgumentIndex(args);
|
||||
}
|
||||
|
||||
if (!hasCorrectTypeArgumentArity(signature, typeArguments)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// If a spread argument is present, check that it corresponds to a rest parameter or at least that it's in the valid range.
|
||||
if (spreadArgIndex >= 0) {
|
||||
return spreadArgIndex >= getMinArgumentCount(signature) && (hasEffectiveRestParameter(signature) || spreadArgIndex < getParameterCount(signature));
|
||||
@@ -18918,6 +18910,43 @@ namespace ts {
|
||||
}
|
||||
}
|
||||
|
||||
function getArgumentArityError(node: Node, signatures: ReadonlyArray<Signature>, args: ReadonlyArray<Expression>) {
|
||||
let min = Number.POSITIVE_INFINITY;
|
||||
let max = Number.NEGATIVE_INFINITY;
|
||||
let belowArgCount = Number.NEGATIVE_INFINITY;
|
||||
let aboveArgCount = Number.POSITIVE_INFINITY;
|
||||
|
||||
let argCount = args.length;
|
||||
for (const sig of signatures) {
|
||||
const minCount = getMinArgumentCount(sig);
|
||||
const maxCount = getParameterCount(sig);
|
||||
if (minCount < argCount && minCount > belowArgCount) belowArgCount = minCount;
|
||||
if (argCount < maxCount && maxCount < aboveArgCount) aboveArgCount = maxCount;
|
||||
min = Math.min(min, minCount);
|
||||
max = Math.max(max, maxCount);
|
||||
}
|
||||
|
||||
const hasRestParameter = some(signatures, hasEffectiveRestParameter);
|
||||
const paramRange = hasRestParameter ? min :
|
||||
min < max ? min + "-" + max :
|
||||
min;
|
||||
const hasSpreadArgument = getSpreadArgumentIndex(args) > -1;
|
||||
if (argCount <= max && hasSpreadArgument) {
|
||||
argCount--;
|
||||
}
|
||||
|
||||
if (hasRestParameter || hasSpreadArgument) {
|
||||
const error = hasRestParameter && hasSpreadArgument ? Diagnostics.Expected_at_least_0_arguments_but_got_1_or_more :
|
||||
hasRestParameter ? Diagnostics.Expected_at_least_0_arguments_but_got_1 :
|
||||
Diagnostics.Expected_0_arguments_but_got_1_or_more;
|
||||
return createDiagnosticForNode(node, error, paramRange, argCount);
|
||||
}
|
||||
if (min < argCount && argCount < max) {
|
||||
return createDiagnosticForNode(node, Diagnostics.No_overload_expects_0_arguments_but_overloads_do_exist_that_expect_either_1_or_2_arguments, argCount, belowArgCount, aboveArgCount);
|
||||
}
|
||||
return createDiagnosticForNode(node, Diagnostics.Expected_0_arguments_but_got_1, paramRange, argCount);
|
||||
}
|
||||
|
||||
function getTypeArgumentArityError(node: Node, signatures: ReadonlyArray<Signature>, typeArguments: NodeArray<TypeNode>) {
|
||||
let min = Infinity;
|
||||
let max = -Infinity;
|
||||
@@ -19008,6 +19037,7 @@ namespace ts {
|
||||
// foo<number>(0);
|
||||
//
|
||||
let candidateForArgumentError: Signature | undefined;
|
||||
let candidateForArgumentArityError: Signature | undefined;
|
||||
let candidateForTypeArgumentError: Signature | undefined;
|
||||
let result: Signature | undefined;
|
||||
|
||||
@@ -19052,6 +19082,9 @@ namespace ts {
|
||||
// an error, we don't need to exclude any arguments, although it would cause no harm to do so.
|
||||
checkApplicableSignature(node, args!, candidateForArgumentError, assignableRelation, /*excludeArgument*/ undefined, /*reportErrors*/ true);
|
||||
}
|
||||
else if (candidateForArgumentArityError) {
|
||||
diagnostics.add(getArgumentArityError(node, [candidateForArgumentArityError], args!));
|
||||
}
|
||||
else if (candidateForTypeArgumentError) {
|
||||
checkTypeArguments(candidateForTypeArgumentError, (node as CallExpression | TaggedTemplateExpression).typeArguments!, /*reportErrors*/ true, fallbackError);
|
||||
}
|
||||
@@ -19059,42 +19092,7 @@ namespace ts {
|
||||
diagnostics.add(getTypeArgumentArityError(node, signatures, typeArguments));
|
||||
}
|
||||
else if (args) {
|
||||
let min = Number.POSITIVE_INFINITY;
|
||||
let max = Number.NEGATIVE_INFINITY;
|
||||
let belowArgCount = Number.NEGATIVE_INFINITY;
|
||||
let aboveArgCount = Number.POSITIVE_INFINITY;
|
||||
|
||||
let argCount = args.length;
|
||||
for (const sig of signatures) {
|
||||
const minCount = getMinArgumentCount(sig);
|
||||
const maxCount = getParameterCount(sig);
|
||||
if (minCount < argCount && minCount > belowArgCount) belowArgCount = minCount;
|
||||
if (argCount < maxCount && maxCount < aboveArgCount) aboveArgCount = maxCount;
|
||||
min = Math.min(min, minCount);
|
||||
max = Math.max(max, maxCount);
|
||||
}
|
||||
|
||||
const hasRestParameter = some(signatures, hasEffectiveRestParameter);
|
||||
const paramRange = hasRestParameter ? min :
|
||||
min < max ? min + "-" + max :
|
||||
min;
|
||||
const hasSpreadArgument = getSpreadArgumentIndex(args) > -1;
|
||||
if (argCount <= max && hasSpreadArgument) {
|
||||
argCount--;
|
||||
}
|
||||
|
||||
if (hasRestParameter || hasSpreadArgument) {
|
||||
const error = hasRestParameter && hasSpreadArgument ? Diagnostics.Expected_at_least_0_arguments_but_got_1_or_more :
|
||||
hasRestParameter ? Diagnostics.Expected_at_least_0_arguments_but_got_1 :
|
||||
Diagnostics.Expected_0_arguments_but_got_1_or_more;
|
||||
diagnostics.add(createDiagnosticForNode(node, error, paramRange, argCount));
|
||||
}
|
||||
else if (min < argCount && argCount < max) {
|
||||
diagnostics.add(createDiagnosticForNode(node, Diagnostics.No_overload_expects_0_arguments_but_overloads_do_exist_that_expect_either_1_or_2_arguments, argCount, belowArgCount, aboveArgCount));
|
||||
}
|
||||
else {
|
||||
diagnostics.add(createDiagnosticForNode(node, Diagnostics.Expected_0_arguments_but_got_1, paramRange, argCount));
|
||||
}
|
||||
diagnostics.add(getArgumentArityError(node, signatures, args));
|
||||
}
|
||||
else if (fallbackError) {
|
||||
diagnostics.add(createDiagnosticForNode(node, fallbackError));
|
||||
@@ -19104,11 +19102,12 @@ namespace ts {
|
||||
|
||||
function chooseOverload(candidates: Signature[], relation: Map<RelationComparisonResult>, signatureHelpTrailingComma = false) {
|
||||
candidateForArgumentError = undefined;
|
||||
candidateForArgumentArityError = undefined;
|
||||
candidateForTypeArgumentError = undefined;
|
||||
|
||||
if (isSingleNonGenericCandidate) {
|
||||
const candidate = candidates[0];
|
||||
if (!hasCorrectArity(node, args!, candidate, signatureHelpTrailingComma)) {
|
||||
if (typeArguments || !hasCorrectArity(node, args!, candidate, signatureHelpTrailingComma)) {
|
||||
return undefined;
|
||||
}
|
||||
if (!checkApplicableSignature(node, args!, candidate, relation, excludeArgument, /*reportErrors*/ false)) {
|
||||
@@ -19120,7 +19119,7 @@ namespace ts {
|
||||
|
||||
for (let candidateIndex = 0; candidateIndex < candidates.length; candidateIndex++) {
|
||||
const originalCandidate = candidates[candidateIndex];
|
||||
if (!hasCorrectArity(node, args!, originalCandidate, signatureHelpTrailingComma)) {
|
||||
if (!hasCorrectTypeArgumentArity(originalCandidate, typeArguments) || !hasCorrectArity(node, args!, originalCandidate, signatureHelpTrailingComma)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -19148,6 +19147,12 @@ namespace ts {
|
||||
}
|
||||
const isJavascript = isInJavaScriptFile(candidate.declaration);
|
||||
candidate = getSignatureInstantiation(candidate, typeArgumentTypes, isJavascript);
|
||||
// If the original signature has a rest type parameter, instantiation may produce a
|
||||
// signature with different arity and we need to perform another arity check.
|
||||
if (getRestTypeParameter(originalCandidate) && !hasCorrectArity(node, args!, candidate, signatureHelpTrailingComma)) {
|
||||
candidateForArgumentArityError = candidate;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!checkApplicableSignature(node, args!, candidate, relation, excludeArgument, /*reportErrors*/ false)) {
|
||||
candidateForArgumentError = candidate;
|
||||
|
||||
@@ -1774,6 +1774,15 @@ namespace ts.server {
|
||||
return this.getScriptInfoForNormalizedPath(toNormalizedPath(uncheckedFileName));
|
||||
}
|
||||
|
||||
/* @internal */
|
||||
getScriptInfoOrConfig(uncheckedFileName: string): ScriptInfoOrConfig | undefined {
|
||||
const path = toNormalizedPath(uncheckedFileName);
|
||||
const info = this.getScriptInfoForNormalizedPath(path);
|
||||
if (info) return info;
|
||||
const configProject = this.configuredProjects.get(uncheckedFileName);
|
||||
return configProject && configProject.getCompilerOptions().configFile;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the projects that contain script info through SymLink
|
||||
* Note that this does not return projects in info.containingProjects
|
||||
@@ -2542,4 +2551,11 @@ namespace ts.server {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/* @internal */
|
||||
export type ScriptInfoOrConfig = ScriptInfo | TsConfigSourceFile;
|
||||
/* @internal */
|
||||
export function isConfigFile(config: ScriptInfoOrConfig): config is TsConfigSourceFile {
|
||||
return (config as TsConfigSourceFile).kind !== undefined;
|
||||
}
|
||||
}
|
||||
|
||||
+17
-9
@@ -1763,7 +1763,7 @@ namespace ts.server {
|
||||
this.projectService,
|
||||
project => project.getLanguageService().getEditsForFileRename(oldPath, newPath, formatOptions, preferences),
|
||||
(a, b) => a.fileName === b.fileName);
|
||||
return simplifiedResult ? changes.map(c => this.mapTextChangeToCodeEditUsingScriptInfo(c)) : changes;
|
||||
return simplifiedResult ? changes.map(c => this.mapTextChangeToCodeEditUsingScriptInfoOrConfigFile(c)) : changes;
|
||||
}
|
||||
|
||||
private getCodeFixes(args: protocol.CodeFixRequestArgs, simplifiedResult: boolean): ReadonlyArray<protocol.CodeFixAction> | ReadonlyArray<CodeFixAction> | undefined {
|
||||
@@ -1840,8 +1840,8 @@ namespace ts.server {
|
||||
return mapTextChangesToCodeEditsForFile(change, project.getSourceFileOrConfigFile(this.normalizePath(change.fileName)));
|
||||
}
|
||||
|
||||
private mapTextChangeToCodeEditUsingScriptInfo(change: FileTextChanges): protocol.FileCodeEdits {
|
||||
return mapTextChangesToCodeEditsUsingScriptInfo(change, this.projectService.getScriptInfo(this.normalizePath(change.fileName)));
|
||||
private mapTextChangeToCodeEditUsingScriptInfoOrConfigFile(change: FileTextChanges): protocol.FileCodeEdits {
|
||||
return mapTextChangesToCodeEditsUsingScriptInfoOrConfig(change, this.projectService.getScriptInfoOrConfig(this.normalizePath(change.fileName)));
|
||||
}
|
||||
|
||||
private normalizePath(fileName: string) {
|
||||
@@ -2358,7 +2358,7 @@ namespace ts.server {
|
||||
}
|
||||
|
||||
function mapTextChangesToCodeEditsForFile(textChanges: FileTextChanges, sourceFile: SourceFile | undefined): protocol.FileCodeEdits {
|
||||
Debug.assert(!!textChanges.isNewFile === !sourceFile, "Expected isNewFile for (only) new files", () => JSON.stringify({ isNewFile: textChanges.isNewFile, hasSourceFile: !!sourceFile }));
|
||||
Debug.assert(!!textChanges.isNewFile === !sourceFile, "Expected isNewFile for (only) new files", () => JSON.stringify({ isNewFile: !!textChanges.isNewFile, hasSourceFile: !!sourceFile }));
|
||||
if (sourceFile) {
|
||||
return {
|
||||
fileName: textChanges.fileName,
|
||||
@@ -2370,10 +2370,10 @@ namespace ts.server {
|
||||
}
|
||||
}
|
||||
|
||||
function mapTextChangesToCodeEditsUsingScriptInfo(textChanges: FileTextChanges, scriptInfo: ScriptInfo | undefined): protocol.FileCodeEdits {
|
||||
Debug.assert(!!textChanges.isNewFile === !scriptInfo);
|
||||
function mapTextChangesToCodeEditsUsingScriptInfoOrConfig(textChanges: FileTextChanges, scriptInfo: ScriptInfoOrConfig | undefined): protocol.FileCodeEdits {
|
||||
Debug.assert(!!textChanges.isNewFile === !scriptInfo, "Expected isNewFile for (only) new files", () => JSON.stringify({ isNewFile: !!textChanges.isNewFile, hasScriptInfo: !!scriptInfo }));
|
||||
return scriptInfo
|
||||
? { fileName: textChanges.fileName, textChanges: textChanges.textChanges.map(textChange => convertTextChangeToCodeEditUsingScriptInfo(textChange, scriptInfo)) }
|
||||
? { fileName: textChanges.fileName, textChanges: textChanges.textChanges.map(textChange => convertTextChangeToCodeEditUsingScriptInfoOrConfig(textChange, scriptInfo)) }
|
||||
: convertNewFileTextChangeToCodeEdit(textChanges);
|
||||
}
|
||||
|
||||
@@ -2385,8 +2385,16 @@ namespace ts.server {
|
||||
};
|
||||
}
|
||||
|
||||
function convertTextChangeToCodeEditUsingScriptInfo(change: TextChange, scriptInfo: ScriptInfo) {
|
||||
return { start: scriptInfo.positionToLineOffset(change.span.start), end: scriptInfo.positionToLineOffset(textSpanEnd(change.span)), newText: change.newText };
|
||||
function convertTextChangeToCodeEditUsingScriptInfoOrConfig(change: TextChange, scriptInfo: ScriptInfoOrConfig): protocol.CodeEdit {
|
||||
return { start: positionToLineOffset(scriptInfo, change.span.start), end: positionToLineOffset(scriptInfo, textSpanEnd(change.span)), newText: change.newText };
|
||||
}
|
||||
|
||||
function positionToLineOffset(info: ScriptInfoOrConfig, position: number): protocol.Location {
|
||||
return isConfigFile(info) ? locationFromLineAndCharacter(info.getLineAndCharacterOfPosition(position)) : info.positionToLineOffset(position);
|
||||
}
|
||||
|
||||
function locationFromLineAndCharacter(lc: LineAndCharacter): protocol.Location {
|
||||
return { line: lc.line + 1, offset: lc.character + 1 };
|
||||
}
|
||||
|
||||
function convertNewFileTextChangeToCodeEdit(textChanges: FileTextChanges): protocol.FileCodeEdits {
|
||||
|
||||
@@ -151,7 +151,7 @@ namespace ts {
|
||||
const toImport = oldFromNew !== undefined
|
||||
// If we're at the new location (file was already renamed), need to redo module resolution starting from the old location.
|
||||
// TODO:GH#18217
|
||||
? getSourceFileToImportFromResolved(resolveModuleName(importLiteral.text, oldImportFromPath, program.getCompilerOptions(), host as ModuleResolutionHost), oldToNew, program)
|
||||
? getSourceFileToImportFromResolved(resolveModuleName(importLiteral.text, oldImportFromPath, program.getCompilerOptions(), host as ModuleResolutionHost), oldToNew, host)
|
||||
: getSourceFileToImport(importedModuleSymbol, importLiteral, sourceFile, program, host, oldToNew);
|
||||
|
||||
// Need an update if the imported file moved, or the importing file moved and was using a relative path.
|
||||
@@ -192,18 +192,18 @@ namespace ts {
|
||||
const resolved = host.resolveModuleNames
|
||||
? host.getResolvedModuleWithFailedLookupLocationsFromCache && host.getResolvedModuleWithFailedLookupLocationsFromCache(importLiteral.text, importingSourceFile.fileName)
|
||||
: program.getResolvedModuleWithFailedLookupLocationsFromCache(importLiteral.text, importingSourceFile.fileName);
|
||||
return getSourceFileToImportFromResolved(resolved, oldToNew, program);
|
||||
return getSourceFileToImportFromResolved(resolved, oldToNew, host);
|
||||
}
|
||||
}
|
||||
|
||||
function getSourceFileToImportFromResolved(resolved: ResolvedModuleWithFailedLookupLocations | undefined, oldToNew: PathUpdater, program: Program): ToImport | undefined {
|
||||
function getSourceFileToImportFromResolved(resolved: ResolvedModuleWithFailedLookupLocations | undefined, oldToNew: PathUpdater, host: LanguageServiceHost): ToImport | undefined {
|
||||
return resolved && (
|
||||
(resolved.resolvedModule && getIfInProgram(resolved.resolvedModule.resolvedFileName)) || firstDefined(resolved.failedLookupLocations, getIfInProgram));
|
||||
(resolved.resolvedModule && getIfExists(resolved.resolvedModule.resolvedFileName)) || firstDefined(resolved.failedLookupLocations, getIfExists));
|
||||
|
||||
function getIfInProgram(oldLocation: string): ToImport | undefined {
|
||||
function getIfExists(oldLocation: string): ToImport | undefined {
|
||||
const newLocation = oldToNew(oldLocation);
|
||||
|
||||
return program.getSourceFile(oldLocation) || newLocation !== undefined && program.getSourceFile(newLocation)
|
||||
return host.fileExists!(oldLocation) || newLocation !== undefined && host.fileExists!(newLocation) // TODO: GH#18217
|
||||
? newLocation !== undefined ? { newFileName: newLocation, updated: true } : { newFileName: oldLocation, updated: false }
|
||||
: undefined;
|
||||
}
|
||||
|
||||
@@ -8688,7 +8688,7 @@ export const x = 10;`
|
||||
};
|
||||
const aTsconfig: File = {
|
||||
path: "/a/tsconfig.json",
|
||||
content: "{}",
|
||||
content: JSON.stringify({ files: ["./old.ts", "./user.ts"] }),
|
||||
};
|
||||
const bUserTs: File = {
|
||||
path: "/b/user.ts",
|
||||
@@ -8703,12 +8703,15 @@ export const x = 10;`
|
||||
const session = createSession(host);
|
||||
openFilesForSession([aUserTs, bUserTs], session);
|
||||
|
||||
const renameRequest = makeSessionRequest<protocol.GetEditsForFileRenameRequestArgs>(CommandNames.GetEditsForFileRename, {
|
||||
oldFilePath: "/a/old.ts",
|
||||
const response = executeSessionRequest<protocol.GetEditsForFileRenameRequest, protocol.GetEditsForFileRenameResponse>(session, CommandNames.GetEditsForFileRename, {
|
||||
oldFilePath: aOldTs.path,
|
||||
newFilePath: "/a/new.ts",
|
||||
});
|
||||
const response = session.executeCommand(renameRequest).response as protocol.GetEditsForFileRenameResponse["body"];
|
||||
assert.deepEqual(response, [
|
||||
assert.deepEqual<ReadonlyArray<protocol.FileCodeEdits>>(response, [
|
||||
{
|
||||
fileName: aTsconfig.path,
|
||||
textChanges: [{ ...protocolTextSpanFromSubstring(aTsconfig.content, "./old.ts"), newText: "new.ts" }],
|
||||
},
|
||||
{
|
||||
fileName: aUserTs.path,
|
||||
textChanges: [{ ...protocolTextSpanFromSubstring(aUserTs.content, "./old"), newText: "./new" }],
|
||||
@@ -8719,6 +8722,31 @@ export const x = 10;`
|
||||
},
|
||||
]);
|
||||
});
|
||||
|
||||
it("works with file moved to inferred project", () => {
|
||||
const aTs: File = { path: "/a.ts", content: 'import {} from "./b";' };
|
||||
const cTs: File = { path: "/c.ts", content: "export {};" };
|
||||
const tsconfig: File = { path: "/tsconfig.json", content: JSON.stringify({ files: ["./a.ts", "./b.ts"] }) };
|
||||
|
||||
const host = createServerHost([aTs, cTs, tsconfig]);
|
||||
const session = createSession(host);
|
||||
openFilesForSession([aTs, cTs], session);
|
||||
|
||||
const response = executeSessionRequest<protocol.GetEditsForFileRenameRequest, protocol.GetEditsForFileRenameResponse>(session, CommandNames.GetEditsForFileRename, {
|
||||
oldFilePath: "/b.ts",
|
||||
newFilePath: cTs.path,
|
||||
});
|
||||
assert.deepEqual<ReadonlyArray<protocol.FileCodeEdits>>(response, [
|
||||
{
|
||||
fileName: "/tsconfig.json",
|
||||
textChanges: [{ ...protocolTextSpanFromSubstring(tsconfig.content, "./b.ts"), newText: "c.ts" }],
|
||||
},
|
||||
{
|
||||
fileName: "/a.ts",
|
||||
textChanges: [{ ...protocolTextSpanFromSubstring(aTs.content, "./b"), newText: "./c" }],
|
||||
},
|
||||
]);
|
||||
});
|
||||
});
|
||||
|
||||
describe("tsserverProjectSystem document registry in project service", () => {
|
||||
|
||||
+1
-1
@@ -8893,7 +8893,7 @@ declare namespace ts.server {
|
||||
private mapCodeFixAction;
|
||||
private mapTextChangesToCodeEdits;
|
||||
private mapTextChangeToCodeEdit;
|
||||
private mapTextChangeToCodeEditUsingScriptInfo;
|
||||
private mapTextChangeToCodeEditUsingScriptInfoOrConfigFile;
|
||||
private normalizePath;
|
||||
private convertTextChangeToCodeEdit;
|
||||
private getBraceMatching;
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
tests/cases/conformance/types/rest/genericRestArity.ts(7,1): error TS2554: Expected 3 arguments, but got 1.
|
||||
tests/cases/conformance/types/rest/genericRestArity.ts(8,1): error TS2554: Expected 3 arguments, but got 8.
|
||||
|
||||
|
||||
==== tests/cases/conformance/types/rest/genericRestArity.ts (2 errors) ====
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
handler: (...args: TS) => void,
|
||||
...args: TS): void;
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
!!! error TS2554: Expected 3 arguments, but got 1.
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
!!! error TS2554: Expected 3 arguments, but got 8.
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
//// [genericRestArity.ts]
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
handler: (...args: TS) => void,
|
||||
...args: TS): void;
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
|
||||
|
||||
//// [genericRestArity.js]
|
||||
// Repro from #25559
|
||||
call(function (x, y) { return x + y; });
|
||||
call(function (x, y) { return x + y; }, 1, 2, 3, 4, 5, 6, 7);
|
||||
@@ -0,0 +1,30 @@
|
||||
=== tests/cases/conformance/types/rest/genericRestArity.ts ===
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
>call : Symbol(call, Decl(genericRestArity.ts, 0, 0))
|
||||
>TS : Symbol(TS, Decl(genericRestArity.ts, 2, 22))
|
||||
|
||||
handler: (...args: TS) => void,
|
||||
>handler : Symbol(handler, Decl(genericRestArity.ts, 2, 44))
|
||||
>args : Symbol(args, Decl(genericRestArity.ts, 3, 14))
|
||||
>TS : Symbol(TS, Decl(genericRestArity.ts, 2, 22))
|
||||
|
||||
...args: TS): void;
|
||||
>args : Symbol(args, Decl(genericRestArity.ts, 3, 35))
|
||||
>TS : Symbol(TS, Decl(genericRestArity.ts, 2, 22))
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
>call : Symbol(call, Decl(genericRestArity.ts, 0, 0))
|
||||
>x : Symbol(x, Decl(genericRestArity.ts, 6, 6))
|
||||
>y : Symbol(y, Decl(genericRestArity.ts, 6, 16))
|
||||
>x : Symbol(x, Decl(genericRestArity.ts, 6, 6))
|
||||
>y : Symbol(y, Decl(genericRestArity.ts, 6, 16))
|
||||
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
>call : Symbol(call, Decl(genericRestArity.ts, 0, 0))
|
||||
>x : Symbol(x, Decl(genericRestArity.ts, 7, 6))
|
||||
>y : Symbol(y, Decl(genericRestArity.ts, 7, 16))
|
||||
>x : Symbol(x, Decl(genericRestArity.ts, 7, 6))
|
||||
>y : Symbol(y, Decl(genericRestArity.ts, 7, 16))
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
=== tests/cases/conformance/types/rest/genericRestArity.ts ===
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
>call : <TS extends unknown[]>(handler: (...args: TS) => void, ...args: TS) => void
|
||||
>TS : TS
|
||||
|
||||
handler: (...args: TS) => void,
|
||||
>handler : (...args: TS) => void
|
||||
>args : TS
|
||||
>TS : TS
|
||||
|
||||
...args: TS): void;
|
||||
>args : TS
|
||||
>TS : TS
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
>call((x: number, y: number) => x + y) : any
|
||||
>call : <TS extends unknown[]>(handler: (...args: TS) => void, ...args: TS) => void
|
||||
>(x: number, y: number) => x + y : (x: number, y: number) => number
|
||||
>x : number
|
||||
>y : number
|
||||
>x + y : number
|
||||
>x : number
|
||||
>y : number
|
||||
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
>call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7) : any
|
||||
>call : <TS extends unknown[]>(handler: (...args: TS) => void, ...args: TS) => void
|
||||
>(x: number, y: number) => x + y : (x: number, y: number) => number
|
||||
>x : number
|
||||
>y : number
|
||||
>x + y : number
|
||||
>x : number
|
||||
>y : number
|
||||
>1 : 1
|
||||
>2 : 2
|
||||
>3 : 3
|
||||
>4 : 4
|
||||
>5 : 5
|
||||
>6 : 6
|
||||
>7 : 7
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
tests/cases/conformance/types/rest/genericRestArityStrict.ts(7,6): error TS2345: Argument of type '(x: number, y: number) => number' is not assignable to parameter of type '() => void'.
|
||||
|
||||
|
||||
==== tests/cases/conformance/types/rest/genericRestArityStrict.ts (1 errors) ====
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
handler: (...args: TS) => void,
|
||||
...args: TS): void;
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
!!! error TS2345: Argument of type '(x: number, y: number) => number' is not assignable to parameter of type '() => void'.
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
//// [genericRestArityStrict.ts]
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
handler: (...args: TS) => void,
|
||||
...args: TS): void;
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
|
||||
|
||||
//// [genericRestArityStrict.js]
|
||||
"use strict";
|
||||
// Repro from #25559
|
||||
call(function (x, y) { return x + y; });
|
||||
call(function (x, y) { return x + y; }, 1, 2, 3, 4, 5, 6, 7);
|
||||
@@ -0,0 +1,30 @@
|
||||
=== tests/cases/conformance/types/rest/genericRestArityStrict.ts ===
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
>call : Symbol(call, Decl(genericRestArityStrict.ts, 0, 0))
|
||||
>TS : Symbol(TS, Decl(genericRestArityStrict.ts, 2, 22))
|
||||
|
||||
handler: (...args: TS) => void,
|
||||
>handler : Symbol(handler, Decl(genericRestArityStrict.ts, 2, 44))
|
||||
>args : Symbol(args, Decl(genericRestArityStrict.ts, 3, 14))
|
||||
>TS : Symbol(TS, Decl(genericRestArityStrict.ts, 2, 22))
|
||||
|
||||
...args: TS): void;
|
||||
>args : Symbol(args, Decl(genericRestArityStrict.ts, 3, 35))
|
||||
>TS : Symbol(TS, Decl(genericRestArityStrict.ts, 2, 22))
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
>call : Symbol(call, Decl(genericRestArityStrict.ts, 0, 0))
|
||||
>x : Symbol(x, Decl(genericRestArityStrict.ts, 6, 6))
|
||||
>y : Symbol(y, Decl(genericRestArityStrict.ts, 6, 16))
|
||||
>x : Symbol(x, Decl(genericRestArityStrict.ts, 6, 6))
|
||||
>y : Symbol(y, Decl(genericRestArityStrict.ts, 6, 16))
|
||||
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
>call : Symbol(call, Decl(genericRestArityStrict.ts, 0, 0))
|
||||
>x : Symbol(x, Decl(genericRestArityStrict.ts, 7, 6))
|
||||
>y : Symbol(y, Decl(genericRestArityStrict.ts, 7, 16))
|
||||
>x : Symbol(x, Decl(genericRestArityStrict.ts, 7, 6))
|
||||
>y : Symbol(y, Decl(genericRestArityStrict.ts, 7, 16))
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
=== tests/cases/conformance/types/rest/genericRestArityStrict.ts ===
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
>call : <TS extends unknown[]>(handler: (...args: TS) => void, ...args: TS) => void
|
||||
>TS : TS
|
||||
|
||||
handler: (...args: TS) => void,
|
||||
>handler : (...args: TS) => void
|
||||
>args : TS
|
||||
>TS : TS
|
||||
|
||||
...args: TS): void;
|
||||
>args : TS
|
||||
>TS : TS
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
>call((x: number, y: number) => x + y) : any
|
||||
>call : <TS extends unknown[]>(handler: (...args: TS) => void, ...args: TS) => void
|
||||
>(x: number, y: number) => x + y : (x: number, y: number) => number
|
||||
>x : number
|
||||
>y : number
|
||||
>x + y : number
|
||||
>x : number
|
||||
>y : number
|
||||
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
>call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7) : void
|
||||
>call : <TS extends unknown[]>(handler: (...args: TS) => void, ...args: TS) => void
|
||||
>(x: number, y: number) => x + y : (x: number, y: number) => number
|
||||
>x : number
|
||||
>y : number
|
||||
>x + y : number
|
||||
>x : number
|
||||
>y : number
|
||||
>1 : 1
|
||||
>2 : 2
|
||||
>3 : 3
|
||||
>4 : 4
|
||||
>5 : 5
|
||||
>6 : 6
|
||||
>7 : 7
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
handler: (...args: TS) => void,
|
||||
...args: TS): void;
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
@@ -0,0 +1,10 @@
|
||||
// @strict: true
|
||||
|
||||
// Repro from #25559
|
||||
|
||||
declare function call<TS extends unknown[]>(
|
||||
handler: (...args: TS) => void,
|
||||
...args: TS): void;
|
||||
|
||||
call((x: number, y: number) => x + y);
|
||||
call((x: number, y: number) => x + y, 1, 2, 3, 4, 5, 6, 7);
|
||||
Reference in New Issue
Block a user