Allow calls on unions of dissimilar signatures (#29011)

* Add core of new union signature logic and test - needs intersection signature logic to fully work

* Add inversion of variance for class props lookup from union sig returns

* Fix lints

* Combine parameter names for nicer quick info

* PR feedback 1

* Fix miscopy

* PR feedback round 2

* Remove argument name combining because loc :(

* Nit cleanup round 3

* Reinline getTupleTypeForArgumentAtPos

* Remove a tad more

* No step on sneky off-by-one error
This commit is contained in:
Wesley Wigham
2018-12-19 16:35:01 -08:00
committed by GitHub
parent ab2a38ebef
commit 08022d57c8
18 changed files with 1364 additions and 47 deletions

View File

@@ -6799,7 +6799,12 @@ namespace ts {
// type is the union of the constituent return types.
function getUnionSignatures(signatureLists: ReadonlyArray<ReadonlyArray<Signature>>): Signature[] {
let result: Signature[] | undefined;
let indexWithLengthOverOne: number | undefined;
for (let i = 0; i < signatureLists.length; i++) {
if (signatureLists[i].length === 0) return emptyArray;
if (signatureLists[i].length > 1) {
indexWithLengthOverOne = indexWithLengthOverOne === undefined ? i : -1; // -1 is a signal there are multiple overload sets
}
for (const signature of signatureLists[i]) {
// Only process signatures with parameter lists that aren't already in the result list
if (!result || !findMatchingSignature(result, signature, /*partialMatch*/ false, /*ignoreThisTypes*/ true, /*ignoreReturnTypes*/ true)) {
@@ -6823,9 +6828,91 @@ namespace ts {
}
}
}
if (!length(result) && indexWithLengthOverOne !== -1) {
// No sufficiently similar signature existed to subsume all the other signatures in the union - time to see if we can make a single
// signature that handles all over them. We only do this when there are overloads in only one constituent.
// (Overloads are conditional in nature and having overloads in multiple constituents would necessitate making a power set of
// signatures from the type, whose ordering would be non-obvious)
const masterList = signatureLists[indexWithLengthOverOne !== undefined ? indexWithLengthOverOne : 0];
let results: Signature[] | undefined = masterList.slice();
for (const signatures of signatureLists) {
if (signatures !== masterList) {
const signature = signatures[0];
Debug.assert(!!signature, "getUnionSignatures bails early on empty signature lists and should not have empty lists on second pass");
results = signature.typeParameters && some(results, s => !!s.typeParameters) ? undefined : map(results, sig => combineSignaturesOfUnionMembers(sig, signature));
if (!results) {
break;
}
}
}
result = results;
}
return result || emptyArray;
}
function combineUnionThisParam(left: Symbol | undefined, right: Symbol | undefined): Symbol | undefined {
if (!left || !right) {
return left || right;
}
// A signature `this` type might be a read or a write position... It's very possible that it should be invariant
// and we should refuse to merge signatures if there are `this` types and they do not match. However, so as to be
// permissive when calling, for now, we'll union the `this` types just like the overlapping-union-signature check does
const thisType = getUnionType([getTypeOfSymbol(left), getTypeOfSymbol(right)], UnionReduction.Subtype);
return createSymbolWithType(left, thisType);
}
function combineUnionParameters(left: Signature, right: Signature) {
const longest = getParameterCount(left) >= getParameterCount(right) ? left : right;
const shorter = longest === left ? right : left;
const longestCount = getParameterCount(longest);
const eitherHasEffectiveRest = (hasEffectiveRestParameter(left) || hasEffectiveRestParameter(right));
const needsExtraRestElement = eitherHasEffectiveRest && !hasEffectiveRestParameter(longest);
const params = new Array<Symbol>(longestCount + (needsExtraRestElement ? 1 : 0));
for (let i = 0; i < longestCount; i++) {
const longestParamType = tryGetTypeAtPosition(longest, i)!;
const shorterParamType = tryGetTypeAtPosition(shorter, i) || unknownType;
const unionParamType = getIntersectionType([longestParamType, shorterParamType]);
const isRestParam = eitherHasEffectiveRest && !needsExtraRestElement && i === (longestCount - 1);
const isOptional = i >= getMinArgumentCount(longest) && i >= getMinArgumentCount(shorter);
const leftName = getParameterNameAtPosition(left, i);
const rightName = getParameterNameAtPosition(right, i);
const paramSymbol = createSymbol(
SymbolFlags.FunctionScopedVariable | (isOptional && !isRestParam ? SymbolFlags.Optional : 0),
leftName === rightName ? leftName : `arg${i}` as __String
);
paramSymbol.type = isRestParam ? createArrayType(unionParamType) : unionParamType;
params[i] = paramSymbol;
}
if (needsExtraRestElement) {
const restParamSymbol = createSymbol(SymbolFlags.FunctionScopedVariable, "args" as __String);
restParamSymbol.type = createArrayType(getTypeAtPosition(shorter, longestCount));
params[longestCount] = restParamSymbol;
}
return params;
}
function combineSignaturesOfUnionMembers(left: Signature, right: Signature): Signature {
const declaration = left.declaration;
const params = combineUnionParameters(left, right);
const thisParam = combineUnionThisParam(left.thisParameter, right.thisParameter);
const minArgCount = Math.max(left.minArgumentCount, right.minArgumentCount);
const hasRestParam = left.hasRestParameter || right.hasRestParameter;
const hasLiteralTypes = left.hasLiteralTypes || right.hasLiteralTypes;
const result = createSignature(
declaration,
left.typeParameters || right.typeParameters,
thisParam,
params,
/*resolvedReturnType*/ undefined,
/*resolvedTypePredicate*/ undefined,
minArgCount,
hasRestParam,
hasLiteralTypes
);
result.unionSignatures = concatenate(left.unionSignatures || [left], [right]);
return result;
}
function getUnionIndexInfo(types: ReadonlyArray<Type>, kind: IndexKind): IndexInfo | undefined {
const indexTypes: Type[] = [];
let isAnyReadonly = false;
@@ -17566,6 +17653,26 @@ namespace ts {
}
function getJsxPropsTypeForSignatureFromMember(sig: Signature, forcedLookupLocation: __String) {
if (sig.unionSignatures) {
// JSX Elements using the legacy `props`-field based lookup (eg, react class components) need to treat the `props` member as an input
// instead of an output position when resolving the signature. We need to go back to the input signatures of the composite signature,
// get the type of `props` on each return type individually, and then _intersect them_, rather than union them (as would normally occur
// for a union signature). It's an unfortunate quirk of looking in the output of the signature for the type we want to use for the input.
// The default behavior of `getTypeOfFirstParameterOfSignatureWithFallback` when no `props` member name is defined is much more sane.
const results: Type[] = [];
for (const signature of sig.unionSignatures) {
const instance = getReturnTypeOfSignature(signature);
if (isTypeAny(instance)) {
return instance;
}
const propType = getTypeOfPropertyOfType(instance, forcedLookupLocation);
if (!propType) {
return;
}
results.push(propType);
}
return getIntersectionType(results);
}
const instanceType = getReturnTypeOfSignature(sig);
return isTypeAny(instanceType) ? instanceType : getTypeOfPropertyOfType(instanceType, forcedLookupLocation);
}

View File

@@ -0,0 +1,110 @@
tests/cases/compiler/callsOnComplexSignatures.tsx(38,19): error TS7006: Parameter 'item' implicitly has an 'any' type.
==== tests/cases/compiler/callsOnComplexSignatures.tsx (1 errors) ====
/// <reference path="/.lib/react16.d.ts" />
import React from "react";
// Simple calls from real usecases
function test1() {
type stringType1 = "foo" | "bar";
type stringType2 = "baz" | "bar";
interface Temp1 {
getValue(name: stringType1): number;
}
interface Temp2 {
getValue(name: stringType2): string;
}
function test(t: Temp1 | Temp2) {
const z = t.getValue("bar"); // Should be fine
}
}
function test2() {
interface Messages {
readonly foo: (options: { [key: string]: any, b: number }) => string;
readonly bar: (options: { [key: string]: any, a: string }) => string;
}
const messages: Messages = {
foo: (options) => "Foo",
bar: (options) => "Bar",
};
const test1 = (type: "foo" | "bar") =>
messages[type]({ a: "A", b: 0 });
}
function test3(items: string[] | number[]) {
items.forEach(item => console.log(item));
~~~~
!!! error TS7006: Parameter 'item' implicitly has an 'any' type.
}
function test4(
arg1: ((...objs: {x: number}[]) => number) | ((...objs: {y: number}[]) => number),
arg2: ((a: {x: number}, b: object) => number) | ((a: object, b: {x: number}) => number),
arg3: ((a: {x: number}, ...objs: {y: number}[]) => number) | ((...objs: {x: number}[]) => number),
arg4: ((a?: {x: number}, b?: {x: number}) => number) | ((a?: {y: number}) => number),
arg5: ((a?: {x: number}, ...b: {x: number}[]) => number) | ((a?: {y: number}) => number),
arg6: ((a?: {x: number}, b?: {x: number}) => number) | ((...a: {y: number}[]) => number),
) {
arg1();
arg1({x: 0, y: 0});
arg1({x: 0, y: 0}, {x: 1, y: 1});
arg2({x: 0}, {x: 0});
arg3({x: 0});
arg3({x: 0}, {x: 0, y: 0});
arg3({x: 0}, {x: 0, y: 0}, {x: 0, y: 0});
arg4();
arg4({x: 0, y: 0});
arg4({x: 0, y: 0}, {x: 0});
arg5();
arg5({x: 0, y: 0});
arg5({x: 0, y: 0}, {x: 0});
arg6();
arg6({x: 0, y: 0});
arg6({x: 0, y: 0}, {x: 0, y: 0});
arg6({x: 0, y: 0}, {x: 0, y: 0}, {y: 0});
}
// JSX Tag names
function test5() {
// Pair of non-like intrinsics
function render(url?: string): React.ReactNode {
const Tag = url ? 'a' : 'button';
return <Tag>test</Tag>;
}
// Union of all intrinsics and components of `any`
function App(props: { component:React.ReactType }) {
const Comp: React.ReactType = props.component;
return (<Comp />);
}
// custom components with non-subset props
function render2() {
interface P1 {
p?: boolean;
c?: string;
}
interface P2 {
p?: boolean;
c?: any;
d?: any;
}
var C: React.ComponentType<P1> | React.ComponentType<P2> = null as any;
const a = <C p={true} />;
}
}

View File

@@ -0,0 +1,169 @@
//// [callsOnComplexSignatures.tsx]
/// <reference path="/.lib/react16.d.ts" />
import React from "react";
// Simple calls from real usecases
function test1() {
type stringType1 = "foo" | "bar";
type stringType2 = "baz" | "bar";
interface Temp1 {
getValue(name: stringType1): number;
}
interface Temp2 {
getValue(name: stringType2): string;
}
function test(t: Temp1 | Temp2) {
const z = t.getValue("bar"); // Should be fine
}
}
function test2() {
interface Messages {
readonly foo: (options: { [key: string]: any, b: number }) => string;
readonly bar: (options: { [key: string]: any, a: string }) => string;
}
const messages: Messages = {
foo: (options) => "Foo",
bar: (options) => "Bar",
};
const test1 = (type: "foo" | "bar") =>
messages[type]({ a: "A", b: 0 });
}
function test3(items: string[] | number[]) {
items.forEach(item => console.log(item));
}
function test4(
arg1: ((...objs: {x: number}[]) => number) | ((...objs: {y: number}[]) => number),
arg2: ((a: {x: number}, b: object) => number) | ((a: object, b: {x: number}) => number),
arg3: ((a: {x: number}, ...objs: {y: number}[]) => number) | ((...objs: {x: number}[]) => number),
arg4: ((a?: {x: number}, b?: {x: number}) => number) | ((a?: {y: number}) => number),
arg5: ((a?: {x: number}, ...b: {x: number}[]) => number) | ((a?: {y: number}) => number),
arg6: ((a?: {x: number}, b?: {x: number}) => number) | ((...a: {y: number}[]) => number),
) {
arg1();
arg1({x: 0, y: 0});
arg1({x: 0, y: 0}, {x: 1, y: 1});
arg2({x: 0}, {x: 0});
arg3({x: 0});
arg3({x: 0}, {x: 0, y: 0});
arg3({x: 0}, {x: 0, y: 0}, {x: 0, y: 0});
arg4();
arg4({x: 0, y: 0});
arg4({x: 0, y: 0}, {x: 0});
arg5();
arg5({x: 0, y: 0});
arg5({x: 0, y: 0}, {x: 0});
arg6();
arg6({x: 0, y: 0});
arg6({x: 0, y: 0}, {x: 0, y: 0});
arg6({x: 0, y: 0}, {x: 0, y: 0}, {y: 0});
}
// JSX Tag names
function test5() {
// Pair of non-like intrinsics
function render(url?: string): React.ReactNode {
const Tag = url ? 'a' : 'button';
return <Tag>test</Tag>;
}
// Union of all intrinsics and components of `any`
function App(props: { component:React.ReactType }) {
const Comp: React.ReactType = props.component;
return (<Comp />);
}
// custom components with non-subset props
function render2() {
interface P1 {
p?: boolean;
c?: string;
}
interface P2 {
p?: boolean;
c?: any;
d?: any;
}
var C: React.ComponentType<P1> | React.ComponentType<P2> = null as any;
const a = <C p={true} />;
}
}
//// [callsOnComplexSignatures.js]
"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
exports.__esModule = true;
/// <reference path="react16.d.ts" />
var react_1 = __importDefault(require("react"));
// Simple calls from real usecases
function test1() {
function test(t) {
var z = t.getValue("bar"); // Should be fine
}
}
function test2() {
var messages = {
foo: function (options) { return "Foo"; },
bar: function (options) { return "Bar"; }
};
var test1 = function (type) {
return messages[type]({ a: "A", b: 0 });
};
}
function test3(items) {
items.forEach(function (item) { return console.log(item); });
}
function test4(arg1, arg2, arg3, arg4, arg5, arg6) {
arg1();
arg1({ x: 0, y: 0 });
arg1({ x: 0, y: 0 }, { x: 1, y: 1 });
arg2({ x: 0 }, { x: 0 });
arg3({ x: 0 });
arg3({ x: 0 }, { x: 0, y: 0 });
arg3({ x: 0 }, { x: 0, y: 0 }, { x: 0, y: 0 });
arg4();
arg4({ x: 0, y: 0 });
arg4({ x: 0, y: 0 }, { x: 0 });
arg5();
arg5({ x: 0, y: 0 });
arg5({ x: 0, y: 0 }, { x: 0 });
arg6();
arg6({ x: 0, y: 0 });
arg6({ x: 0, y: 0 }, { x: 0, y: 0 });
arg6({ x: 0, y: 0 }, { x: 0, y: 0 }, { y: 0 });
}
// JSX Tag names
function test5() {
// Pair of non-like intrinsics
function render(url) {
var Tag = url ? 'a' : 'button';
return react_1["default"].createElement(Tag, null, "test");
}
// Union of all intrinsics and components of `any`
function App(props) {
var Comp = props.component;
return (react_1["default"].createElement(Comp, null));
}
// custom components with non-subset props
function render2() {
var C = null;
var a = react_1["default"].createElement(C, { p: true });
}
}

View File

@@ -0,0 +1,334 @@
=== tests/cases/compiler/callsOnComplexSignatures.tsx ===
/// <reference path="react16.d.ts" />
import React from "react";
>React : Symbol(React, Decl(callsOnComplexSignatures.tsx, 1, 6))
// Simple calls from real usecases
function test1() {
>test1 : Symbol(test1, Decl(callsOnComplexSignatures.tsx, 1, 26))
type stringType1 = "foo" | "bar";
>stringType1 : Symbol(stringType1, Decl(callsOnComplexSignatures.tsx, 4, 18))
type stringType2 = "baz" | "bar";
>stringType2 : Symbol(stringType2, Decl(callsOnComplexSignatures.tsx, 5, 37))
interface Temp1 {
>Temp1 : Symbol(Temp1, Decl(callsOnComplexSignatures.tsx, 6, 37))
getValue(name: stringType1): number;
>getValue : Symbol(Temp1.getValue, Decl(callsOnComplexSignatures.tsx, 8, 21))
>name : Symbol(name, Decl(callsOnComplexSignatures.tsx, 9, 17))
>stringType1 : Symbol(stringType1, Decl(callsOnComplexSignatures.tsx, 4, 18))
}
interface Temp2 {
>Temp2 : Symbol(Temp2, Decl(callsOnComplexSignatures.tsx, 10, 5))
getValue(name: stringType2): string;
>getValue : Symbol(Temp2.getValue, Decl(callsOnComplexSignatures.tsx, 12, 21))
>name : Symbol(name, Decl(callsOnComplexSignatures.tsx, 13, 17))
>stringType2 : Symbol(stringType2, Decl(callsOnComplexSignatures.tsx, 5, 37))
}
function test(t: Temp1 | Temp2) {
>test : Symbol(test, Decl(callsOnComplexSignatures.tsx, 14, 5))
>t : Symbol(t, Decl(callsOnComplexSignatures.tsx, 16, 18))
>Temp1 : Symbol(Temp1, Decl(callsOnComplexSignatures.tsx, 6, 37))
>Temp2 : Symbol(Temp2, Decl(callsOnComplexSignatures.tsx, 10, 5))
const z = t.getValue("bar"); // Should be fine
>z : Symbol(z, Decl(callsOnComplexSignatures.tsx, 17, 13))
>t.getValue : Symbol(getValue, Decl(callsOnComplexSignatures.tsx, 8, 21), Decl(callsOnComplexSignatures.tsx, 12, 21))
>t : Symbol(t, Decl(callsOnComplexSignatures.tsx, 16, 18))
>getValue : Symbol(getValue, Decl(callsOnComplexSignatures.tsx, 8, 21), Decl(callsOnComplexSignatures.tsx, 12, 21))
}
}
function test2() {
>test2 : Symbol(test2, Decl(callsOnComplexSignatures.tsx, 19, 1))
interface Messages {
>Messages : Symbol(Messages, Decl(callsOnComplexSignatures.tsx, 21, 18))
readonly foo: (options: { [key: string]: any, b: number }) => string;
>foo : Symbol(Messages.foo, Decl(callsOnComplexSignatures.tsx, 22, 24))
>options : Symbol(options, Decl(callsOnComplexSignatures.tsx, 23, 23))
>key : Symbol(key, Decl(callsOnComplexSignatures.tsx, 23, 35))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 23, 53))
readonly bar: (options: { [key: string]: any, a: string }) => string;
>bar : Symbol(Messages.bar, Decl(callsOnComplexSignatures.tsx, 23, 77))
>options : Symbol(options, Decl(callsOnComplexSignatures.tsx, 24, 23))
>key : Symbol(key, Decl(callsOnComplexSignatures.tsx, 24, 35))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 24, 53))
}
const messages: Messages = {
>messages : Symbol(messages, Decl(callsOnComplexSignatures.tsx, 27, 9))
>Messages : Symbol(Messages, Decl(callsOnComplexSignatures.tsx, 21, 18))
foo: (options) => "Foo",
>foo : Symbol(foo, Decl(callsOnComplexSignatures.tsx, 27, 32))
>options : Symbol(options, Decl(callsOnComplexSignatures.tsx, 28, 14))
bar: (options) => "Bar",
>bar : Symbol(bar, Decl(callsOnComplexSignatures.tsx, 28, 32))
>options : Symbol(options, Decl(callsOnComplexSignatures.tsx, 29, 14))
};
const test1 = (type: "foo" | "bar") =>
>test1 : Symbol(test1, Decl(callsOnComplexSignatures.tsx, 32, 9))
>type : Symbol(type, Decl(callsOnComplexSignatures.tsx, 32, 19))
messages[type]({ a: "A", b: 0 });
>messages : Symbol(messages, Decl(callsOnComplexSignatures.tsx, 27, 9))
>type : Symbol(type, Decl(callsOnComplexSignatures.tsx, 32, 19))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 33, 24))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 33, 32))
}
function test3(items: string[] | number[]) {
>test3 : Symbol(test3, Decl(callsOnComplexSignatures.tsx, 34, 1))
>items : Symbol(items, Decl(callsOnComplexSignatures.tsx, 36, 15))
items.forEach(item => console.log(item));
>items.forEach : Symbol(forEach, Decl(lib.es5.d.ts, --, --), Decl(lib.es5.d.ts, --, --))
>items : Symbol(items, Decl(callsOnComplexSignatures.tsx, 36, 15))
>forEach : Symbol(forEach, Decl(lib.es5.d.ts, --, --), Decl(lib.es5.d.ts, --, --))
>item : Symbol(item, Decl(callsOnComplexSignatures.tsx, 37, 18))
>console.log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --))
>console : Symbol(console, Decl(lib.dom.d.ts, --, --))
>log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --))
>item : Symbol(item, Decl(callsOnComplexSignatures.tsx, 37, 18))
}
function test4(
>test4 : Symbol(test4, Decl(callsOnComplexSignatures.tsx, 38, 1))
arg1: ((...objs: {x: number}[]) => number) | ((...objs: {y: number}[]) => number),
>arg1 : Symbol(arg1, Decl(callsOnComplexSignatures.tsx, 40, 15))
>objs : Symbol(objs, Decl(callsOnComplexSignatures.tsx, 41, 12))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 41, 22))
>objs : Symbol(objs, Decl(callsOnComplexSignatures.tsx, 41, 51))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 41, 61))
arg2: ((a: {x: number}, b: object) => number) | ((a: object, b: {x: number}) => number),
>arg2 : Symbol(arg2, Decl(callsOnComplexSignatures.tsx, 41, 86))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 42, 12))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 42, 16))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 42, 27))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 42, 54))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 42, 64))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 42, 69))
arg3: ((a: {x: number}, ...objs: {y: number}[]) => number) | ((...objs: {x: number}[]) => number),
>arg3 : Symbol(arg3, Decl(callsOnComplexSignatures.tsx, 42, 92))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 43, 12))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 43, 16))
>objs : Symbol(objs, Decl(callsOnComplexSignatures.tsx, 43, 27))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 43, 38))
>objs : Symbol(objs, Decl(callsOnComplexSignatures.tsx, 43, 67))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 43, 77))
arg4: ((a?: {x: number}, b?: {x: number}) => number) | ((a?: {y: number}) => number),
>arg4 : Symbol(arg4, Decl(callsOnComplexSignatures.tsx, 43, 102))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 44, 12))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 44, 17))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 44, 28))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 44, 34))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 44, 61))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 44, 66))
arg5: ((a?: {x: number}, ...b: {x: number}[]) => number) | ((a?: {y: number}) => number),
>arg5 : Symbol(arg5, Decl(callsOnComplexSignatures.tsx, 44, 89))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 45, 12))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 45, 17))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 45, 28))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 45, 36))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 45, 65))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 45, 70))
arg6: ((a?: {x: number}, b?: {x: number}) => number) | ((...a: {y: number}[]) => number),
>arg6 : Symbol(arg6, Decl(callsOnComplexSignatures.tsx, 45, 93))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 46, 12))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 46, 17))
>b : Symbol(b, Decl(callsOnComplexSignatures.tsx, 46, 28))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 46, 34))
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 46, 61))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 46, 68))
) {
arg1();
>arg1 : Symbol(arg1, Decl(callsOnComplexSignatures.tsx, 40, 15))
arg1({x: 0, y: 0});
>arg1 : Symbol(arg1, Decl(callsOnComplexSignatures.tsx, 40, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 49, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 49, 15))
arg1({x: 0, y: 0}, {x: 1, y: 1});
>arg1 : Symbol(arg1, Decl(callsOnComplexSignatures.tsx, 40, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 50, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 50, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 50, 24))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 50, 29))
arg2({x: 0}, {x: 0});
>arg2 : Symbol(arg2, Decl(callsOnComplexSignatures.tsx, 41, 86))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 52, 10))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 52, 18))
arg3({x: 0});
>arg3 : Symbol(arg3, Decl(callsOnComplexSignatures.tsx, 42, 92))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 54, 10))
arg3({x: 0}, {x: 0, y: 0});
>arg3 : Symbol(arg3, Decl(callsOnComplexSignatures.tsx, 42, 92))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 55, 10))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 55, 18))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 55, 23))
arg3({x: 0}, {x: 0, y: 0}, {x: 0, y: 0});
>arg3 : Symbol(arg3, Decl(callsOnComplexSignatures.tsx, 42, 92))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 56, 10))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 56, 18))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 56, 23))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 56, 32))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 56, 37))
arg4();
>arg4 : Symbol(arg4, Decl(callsOnComplexSignatures.tsx, 43, 102))
arg4({x: 0, y: 0});
>arg4 : Symbol(arg4, Decl(callsOnComplexSignatures.tsx, 43, 102))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 59, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 59, 15))
arg4({x: 0, y: 0}, {x: 0});
>arg4 : Symbol(arg4, Decl(callsOnComplexSignatures.tsx, 43, 102))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 60, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 60, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 60, 24))
arg5();
>arg5 : Symbol(arg5, Decl(callsOnComplexSignatures.tsx, 44, 89))
arg5({x: 0, y: 0});
>arg5 : Symbol(arg5, Decl(callsOnComplexSignatures.tsx, 44, 89))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 63, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 63, 15))
arg5({x: 0, y: 0}, {x: 0});
>arg5 : Symbol(arg5, Decl(callsOnComplexSignatures.tsx, 44, 89))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 64, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 64, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 64, 24))
arg6();
>arg6 : Symbol(arg6, Decl(callsOnComplexSignatures.tsx, 45, 93))
arg6({x: 0, y: 0});
>arg6 : Symbol(arg6, Decl(callsOnComplexSignatures.tsx, 45, 93))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 67, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 67, 15))
arg6({x: 0, y: 0}, {x: 0, y: 0});
>arg6 : Symbol(arg6, Decl(callsOnComplexSignatures.tsx, 45, 93))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 68, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 68, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 68, 24))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 68, 29))
arg6({x: 0, y: 0}, {x: 0, y: 0}, {y: 0});
>arg6 : Symbol(arg6, Decl(callsOnComplexSignatures.tsx, 45, 93))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 69, 10))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 69, 15))
>x : Symbol(x, Decl(callsOnComplexSignatures.tsx, 69, 24))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 69, 29))
>y : Symbol(y, Decl(callsOnComplexSignatures.tsx, 69, 38))
}
// JSX Tag names
function test5() {
>test5 : Symbol(test5, Decl(callsOnComplexSignatures.tsx, 70, 1))
// Pair of non-like intrinsics
function render(url?: string): React.ReactNode {
>render : Symbol(render, Decl(callsOnComplexSignatures.tsx, 73, 18))
>url : Symbol(url, Decl(callsOnComplexSignatures.tsx, 75, 20))
>React : Symbol(React, Decl(callsOnComplexSignatures.tsx, 1, 6))
>ReactNode : Symbol(React.ReactNode, Decl(react16.d.ts, 216, 49))
const Tag = url ? 'a' : 'button';
>Tag : Symbol(Tag, Decl(callsOnComplexSignatures.tsx, 76, 13))
>url : Symbol(url, Decl(callsOnComplexSignatures.tsx, 75, 20))
return <Tag>test</Tag>;
>Tag : Symbol(Tag, Decl(callsOnComplexSignatures.tsx, 76, 13))
>Tag : Symbol(Tag, Decl(callsOnComplexSignatures.tsx, 76, 13))
}
// Union of all intrinsics and components of `any`
function App(props: { component:React.ReactType }) {
>App : Symbol(App, Decl(callsOnComplexSignatures.tsx, 78, 5))
>props : Symbol(props, Decl(callsOnComplexSignatures.tsx, 81, 17))
>component : Symbol(component, Decl(callsOnComplexSignatures.tsx, 81, 25))
>React : Symbol(React, Decl(callsOnComplexSignatures.tsx, 1, 6))
>ReactType : Symbol(React.ReactType, Decl(react16.d.ts, 112, 21))
const Comp: React.ReactType = props.component;
>Comp : Symbol(Comp, Decl(callsOnComplexSignatures.tsx, 82, 13))
>React : Symbol(React, Decl(callsOnComplexSignatures.tsx, 1, 6))
>ReactType : Symbol(React.ReactType, Decl(react16.d.ts, 112, 21))
>props.component : Symbol(component, Decl(callsOnComplexSignatures.tsx, 81, 25))
>props : Symbol(props, Decl(callsOnComplexSignatures.tsx, 81, 17))
>component : Symbol(component, Decl(callsOnComplexSignatures.tsx, 81, 25))
return (<Comp />);
>Comp : Symbol(Comp, Decl(callsOnComplexSignatures.tsx, 82, 13))
}
// custom components with non-subset props
function render2() {
>render2 : Symbol(render2, Decl(callsOnComplexSignatures.tsx, 84, 5))
interface P1 {
>P1 : Symbol(P1, Decl(callsOnComplexSignatures.tsx, 87, 24))
p?: boolean;
>p : Symbol(P1.p, Decl(callsOnComplexSignatures.tsx, 88, 22))
c?: string;
>c : Symbol(P1.c, Decl(callsOnComplexSignatures.tsx, 89, 24))
}
interface P2 {
>P2 : Symbol(P2, Decl(callsOnComplexSignatures.tsx, 91, 9))
p?: boolean;
>p : Symbol(P2.p, Decl(callsOnComplexSignatures.tsx, 92, 22))
c?: any;
>c : Symbol(P2.c, Decl(callsOnComplexSignatures.tsx, 93, 24))
d?: any;
>d : Symbol(P2.d, Decl(callsOnComplexSignatures.tsx, 94, 20))
}
var C: React.ComponentType<P1> | React.ComponentType<P2> = null as any;
>C : Symbol(C, Decl(callsOnComplexSignatures.tsx, 98, 11))
>React : Symbol(React, Decl(callsOnComplexSignatures.tsx, 1, 6))
>ComponentType : Symbol(React.ComponentType, Decl(react16.d.ts, 117, 60))
>P1 : Symbol(P1, Decl(callsOnComplexSignatures.tsx, 87, 24))
>React : Symbol(React, Decl(callsOnComplexSignatures.tsx, 1, 6))
>ComponentType : Symbol(React.ComponentType, Decl(react16.d.ts, 117, 60))
>P2 : Symbol(P2, Decl(callsOnComplexSignatures.tsx, 91, 9))
const a = <C p={true} />;
>a : Symbol(a, Decl(callsOnComplexSignatures.tsx, 100, 13))
>C : Symbol(C, Decl(callsOnComplexSignatures.tsx, 98, 11))
>p : Symbol(p, Decl(callsOnComplexSignatures.tsx, 100, 20))
}
}

View File

@@ -0,0 +1,416 @@
=== tests/cases/compiler/callsOnComplexSignatures.tsx ===
/// <reference path="react16.d.ts" />
import React from "react";
>React : typeof React
// Simple calls from real usecases
function test1() {
>test1 : () => void
type stringType1 = "foo" | "bar";
>stringType1 : "foo" | "bar"
type stringType2 = "baz" | "bar";
>stringType2 : "bar" | "baz"
interface Temp1 {
getValue(name: stringType1): number;
>getValue : (name: "foo" | "bar") => number
>name : "foo" | "bar"
}
interface Temp2 {
getValue(name: stringType2): string;
>getValue : (name: "bar" | "baz") => string
>name : "bar" | "baz"
}
function test(t: Temp1 | Temp2) {
>test : (t: Temp1 | Temp2) => void
>t : Temp1 | Temp2
const z = t.getValue("bar"); // Should be fine
>z : React.ReactText
>t.getValue("bar") : React.ReactText
>t.getValue : ((name: "foo" | "bar") => number) | ((name: "bar" | "baz") => string)
>t : Temp1 | Temp2
>getValue : ((name: "foo" | "bar") => number) | ((name: "bar" | "baz") => string)
>"bar" : "bar"
}
}
function test2() {
>test2 : () => void
interface Messages {
readonly foo: (options: { [key: string]: any, b: number }) => string;
>foo : (options: { [key: string]: any; b: number; }) => string
>options : { [key: string]: any; b: number; }
>key : string
>b : number
readonly bar: (options: { [key: string]: any, a: string }) => string;
>bar : (options: { [key: string]: any; a: string; }) => string
>options : { [key: string]: any; a: string; }
>key : string
>a : string
}
const messages: Messages = {
>messages : Messages
>{ foo: (options) => "Foo", bar: (options) => "Bar", } : { foo: (options: { [key: string]: any; b: number; }) => string; bar: (options: { [key: string]: any; a: string; }) => string; }
foo: (options) => "Foo",
>foo : (options: { [key: string]: any; b: number; }) => string
>(options) => "Foo" : (options: { [key: string]: any; b: number; }) => string
>options : { [key: string]: any; b: number; }
>"Foo" : "Foo"
bar: (options) => "Bar",
>bar : (options: { [key: string]: any; a: string; }) => string
>(options) => "Bar" : (options: { [key: string]: any; a: string; }) => string
>options : { [key: string]: any; a: string; }
>"Bar" : "Bar"
};
const test1 = (type: "foo" | "bar") =>
>test1 : (type: "foo" | "bar") => string
>(type: "foo" | "bar") => messages[type]({ a: "A", b: 0 }) : (type: "foo" | "bar") => string
>type : "foo" | "bar"
messages[type]({ a: "A", b: 0 });
>messages[type]({ a: "A", b: 0 }) : string
>messages[type] : ((options: { [key: string]: any; b: number; }) => string) | ((options: { [key: string]: any; a: string; }) => string)
>messages : Messages
>type : "foo" | "bar"
>{ a: "A", b: 0 } : { a: string; b: number; }
>a : string
>"A" : "A"
>b : number
>0 : 0
}
function test3(items: string[] | number[]) {
>test3 : (items: string[] | number[]) => void
>items : string[] | number[]
items.forEach(item => console.log(item));
>items.forEach(item => console.log(item)) : void
>items.forEach : ((callbackfn: (value: string, index: number, array: string[]) => void, thisArg?: any) => void) | ((callbackfn: (value: number, index: number, array: number[]) => void, thisArg?: any) => void)
>items : string[] | number[]
>forEach : ((callbackfn: (value: string, index: number, array: string[]) => void, thisArg?: any) => void) | ((callbackfn: (value: number, index: number, array: number[]) => void, thisArg?: any) => void)
>item => console.log(item) : (item: any) => void
>item : any
>console.log(item) : void
>console.log : (message?: any, ...optionalParams: any[]) => void
>console : Console
>log : (message?: any, ...optionalParams: any[]) => void
>item : any
}
function test4(
>test4 : (arg1: ((...objs: { x: number; }[]) => number) | ((...objs: { y: number; }[]) => number), arg2: ((a: { x: number; }, b: object) => number) | ((a: object, b: { x: number; }) => number), arg3: ((a: { x: number; }, ...objs: { y: number; }[]) => number) | ((...objs: { x: number; }[]) => number), arg4: ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((a?: { y: number; } | undefined) => number), arg5: ((a?: { x: number; } | undefined, ...b: { x: number; }[]) => number) | ((a?: { y: number; } | undefined) => number), arg6: ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((...a: { y: number; }[]) => number)) => void
arg1: ((...objs: {x: number}[]) => number) | ((...objs: {y: number}[]) => number),
>arg1 : ((...objs: { x: number; }[]) => number) | ((...objs: { y: number; }[]) => number)
>objs : { x: number; }[]
>x : number
>objs : { y: number; }[]
>y : number
arg2: ((a: {x: number}, b: object) => number) | ((a: object, b: {x: number}) => number),
>arg2 : ((a: { x: number; }, b: object) => number) | ((a: object, b: { x: number; }) => number)
>a : { x: number; }
>x : number
>b : object
>a : object
>b : { x: number; }
>x : number
arg3: ((a: {x: number}, ...objs: {y: number}[]) => number) | ((...objs: {x: number}[]) => number),
>arg3 : ((a: { x: number; }, ...objs: { y: number; }[]) => number) | ((...objs: { x: number; }[]) => number)
>a : { x: number; }
>x : number
>objs : { y: number; }[]
>y : number
>objs : { x: number; }[]
>x : number
arg4: ((a?: {x: number}, b?: {x: number}) => number) | ((a?: {y: number}) => number),
>arg4 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((a?: { y: number; } | undefined) => number)
>a : { x: number; } | undefined
>x : number
>b : { x: number; } | undefined
>x : number
>a : { y: number; } | undefined
>y : number
arg5: ((a?: {x: number}, ...b: {x: number}[]) => number) | ((a?: {y: number}) => number),
>arg5 : ((a?: { x: number; } | undefined, ...b: { x: number; }[]) => number) | ((a?: { y: number; } | undefined) => number)
>a : { x: number; } | undefined
>x : number
>b : { x: number; }[]
>x : number
>a : { y: number; } | undefined
>y : number
arg6: ((a?: {x: number}, b?: {x: number}) => number) | ((...a: {y: number}[]) => number),
>arg6 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((...a: { y: number; }[]) => number)
>a : { x: number; } | undefined
>x : number
>b : { x: number; } | undefined
>x : number
>a : { y: number; }[]
>y : number
) {
arg1();
>arg1() : number
>arg1 : ((...objs: { x: number; }[]) => number) | ((...objs: { y: number; }[]) => number)
arg1({x: 0, y: 0});
>arg1({x: 0, y: 0}) : number
>arg1 : ((...objs: { x: number; }[]) => number) | ((...objs: { y: number; }[]) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg1({x: 0, y: 0}, {x: 1, y: 1});
>arg1({x: 0, y: 0}, {x: 1, y: 1}) : number
>arg1 : ((...objs: { x: number; }[]) => number) | ((...objs: { y: number; }[]) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{x: 1, y: 1} : { x: number; y: number; }
>x : number
>1 : 1
>y : number
>1 : 1
arg2({x: 0}, {x: 0});
>arg2({x: 0}, {x: 0}) : number
>arg2 : ((a: { x: number; }, b: object) => number) | ((a: object, b: { x: number; }) => number)
>{x: 0} : { x: number; }
>x : number
>0 : 0
>{x: 0} : { x: number; }
>x : number
>0 : 0
arg3({x: 0});
>arg3({x: 0}) : number
>arg3 : ((a: { x: number; }, ...objs: { y: number; }[]) => number) | ((...objs: { x: number; }[]) => number)
>{x: 0} : { x: number; }
>x : number
>0 : 0
arg3({x: 0}, {x: 0, y: 0});
>arg3({x: 0}, {x: 0, y: 0}) : number
>arg3 : ((a: { x: number; }, ...objs: { y: number; }[]) => number) | ((...objs: { x: number; }[]) => number)
>{x: 0} : { x: number; }
>x : number
>0 : 0
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg3({x: 0}, {x: 0, y: 0}, {x: 0, y: 0});
>arg3({x: 0}, {x: 0, y: 0}, {x: 0, y: 0}) : number
>arg3 : ((a: { x: number; }, ...objs: { y: number; }[]) => number) | ((...objs: { x: number; }[]) => number)
>{x: 0} : { x: number; }
>x : number
>0 : 0
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg4();
>arg4() : number
>arg4 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((a?: { y: number; } | undefined) => number)
arg4({x: 0, y: 0});
>arg4({x: 0, y: 0}) : number
>arg4 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((a?: { y: number; } | undefined) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg4({x: 0, y: 0}, {x: 0});
>arg4({x: 0, y: 0}, {x: 0}) : number
>arg4 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((a?: { y: number; } | undefined) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{x: 0} : { x: number; }
>x : number
>0 : 0
arg5();
>arg5() : number
>arg5 : ((a?: { x: number; } | undefined, ...b: { x: number; }[]) => number) | ((a?: { y: number; } | undefined) => number)
arg5({x: 0, y: 0});
>arg5({x: 0, y: 0}) : number
>arg5 : ((a?: { x: number; } | undefined, ...b: { x: number; }[]) => number) | ((a?: { y: number; } | undefined) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg5({x: 0, y: 0}, {x: 0});
>arg5({x: 0, y: 0}, {x: 0}) : number
>arg5 : ((a?: { x: number; } | undefined, ...b: { x: number; }[]) => number) | ((a?: { y: number; } | undefined) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{x: 0} : { x: number; }
>x : number
>0 : 0
arg6();
>arg6() : number
>arg6 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((...a: { y: number; }[]) => number)
arg6({x: 0, y: 0});
>arg6({x: 0, y: 0}) : number
>arg6 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((...a: { y: number; }[]) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg6({x: 0, y: 0}, {x: 0, y: 0});
>arg6({x: 0, y: 0}, {x: 0, y: 0}) : number
>arg6 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((...a: { y: number; }[]) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
arg6({x: 0, y: 0}, {x: 0, y: 0}, {y: 0});
>arg6({x: 0, y: 0}, {x: 0, y: 0}, {y: 0}) : number
>arg6 : ((a?: { x: number; } | undefined, b?: { x: number; } | undefined) => number) | ((...a: { y: number; }[]) => number)
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{x: 0, y: 0} : { x: number; y: number; }
>x : number
>0 : 0
>y : number
>0 : 0
>{y: 0} : { y: number; }
>y : number
>0 : 0
}
// JSX Tag names
function test5() {
>test5 : () => void
// Pair of non-like intrinsics
function render(url?: string): React.ReactNode {
>render : (url?: string | undefined) => React.ReactNode
>url : string | undefined
>React : any
const Tag = url ? 'a' : 'button';
>Tag : "a" | "button"
>url ? 'a' : 'button' : "a" | "button"
>url : string | undefined
>'a' : "a"
>'button' : "button"
return <Tag>test</Tag>;
><Tag>test</Tag> : JSX.Element
>Tag : "a" | "button"
>Tag : "a" | "button"
}
// Union of all intrinsics and components of `any`
function App(props: { component:React.ReactType }) {
>App : (props: { component: React.ReactType<any>; }) => JSX.Element
>props : { component: React.ReactType<any>; }
>component : React.ReactType<any>
>React : any
const Comp: React.ReactType = props.component;
>Comp : React.ReactType<any>
>React : any
>props.component : React.ReactType<any>
>props : { component: React.ReactType<any>; }
>component : React.ReactType<any>
return (<Comp />);
>(<Comp />) : JSX.Element
><Comp /> : JSX.Element
>Comp : React.ReactType<any>
}
// custom components with non-subset props
function render2() {
>render2 : () => void
interface P1 {
p?: boolean;
>p : boolean | undefined
c?: string;
>c : string | undefined
}
interface P2 {
p?: boolean;
>p : boolean | undefined
c?: any;
>c : any
d?: any;
>d : any
}
var C: React.ComponentType<P1> | React.ComponentType<P2> = null as any;
>C : React.ComponentClass<P1, any> | React.StatelessComponent<P1> | React.ComponentClass<P2, any> | React.StatelessComponent<P2>
>React : any
>React : any
>null as any : any
>null : null
const a = <C p={true} />;
>a : JSX.Element
><C p={true} /> : JSX.Element
>C : React.ComponentClass<P1, any> | React.StatelessComponent<P1> | React.ComponentClass<P2, any> | React.StatelessComponent<P2>
>p : true
>true : true
}
}

View File

@@ -6,7 +6,7 @@ tests/cases/compiler/controlFlowArrayErrors.ts(19,9): error TS7034: Variable 'x'
tests/cases/compiler/controlFlowArrayErrors.ts(22,9): error TS7005: Variable 'x' implicitly has an 'any[]' type.
tests/cases/compiler/controlFlowArrayErrors.ts(29,12): error TS2345: Argument of type 'true' is not assignable to parameter of type 'string | number'.
tests/cases/compiler/controlFlowArrayErrors.ts(34,12): error TS2345: Argument of type 'true' is not assignable to parameter of type 'string | number'.
tests/cases/compiler/controlFlowArrayErrors.ts(48,5): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((...items: (string | number)[]) => number) | ((...items: boolean[]) => number)' has no compatible call signatures.
tests/cases/compiler/controlFlowArrayErrors.ts(48,12): error TS2345: Argument of type '99' is not assignable to parameter of type 'never'.
tests/cases/compiler/controlFlowArrayErrors.ts(56,12): error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number'.
tests/cases/compiler/controlFlowArrayErrors.ts(60,11): error TS7034: Variable 'x' implicitly has type 'any[]' in some locations where its type cannot be determined.
tests/cases/compiler/controlFlowArrayErrors.ts(63,9): error TS7005: Variable 'x' implicitly has an 'any[]' type.
@@ -77,8 +77,8 @@ tests/cases/compiler/controlFlowArrayErrors.ts(63,9): error TS7005: Variable 'x'
}
x; // boolean[] | (string | number)[]
x.push(99); // Error
~~~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((...items: (string | number)[]) => number) | ((...items: boolean[]) => number)' has no compatible call signatures.
~~
!!! error TS2345: Argument of type '99' is not assignable to parameter of type 'never'.
}
function f7() {

View File

@@ -1,7 +1,7 @@
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(11,3): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(15,3): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(18,3): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(19,3): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(11,7): error TS2345: Argument of type '"s"' is not assignable to parameter of type 'never'.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(15,7): error TS2345: Argument of type '"s"' is not assignable to parameter of type 'never'.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(18,5): error TS2345: Argument of type '""' is not assignable to parameter of type 'never'.
tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(19,3): error TS2554: Expected 1 arguments, but got 4.
==== tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts (4 errors) ====
@@ -16,20 +16,20 @@ tests/cases/compiler/functionCallOnConstrainedTypeVariable.ts(19,3): error TS234
function call0(p: A | B) {
p.a("s"); // Error
~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
~~~
!!! error TS2345: Argument of type '"s"' is not assignable to parameter of type 'never'.
}
function callN<T extends A | B>(p: T) {
p.a("s"); // Error
~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
~~~
!!! error TS2345: Argument of type '"s"' is not assignable to parameter of type 'never'.
var a: T["a"] = p.a;
a(""); // Error
~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
~~
!!! error TS2345: Argument of type '""' is not assignable to parameter of type 'never'.
a("", "", "", ""); // Error
~~~~~~~~~~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((x: number) => string) | ((x: boolean) => string)' has no compatible call signatures.
!!! error TS2554: Expected 1 arguments, but got 4.
}

View File

@@ -1,4 +1,4 @@
tests/cases/conformance/jsx/file.tsx(12,2): error TS2604: JSX element type 'SFCComp' does not have any construct or call signatures.
tests/cases/conformance/jsx/file.tsx(12,10): error TS2322: Type 'true' is not assignable to type 'never'.
==== tests/cases/conformance/jsx/file.tsx (1 errors) ====
@@ -14,5 +14,6 @@ tests/cases/conformance/jsx/file.tsx(12,2): error TS2604: JSX element type 'SFCC
var SFCComp = SFC1 || SFC2;
<SFCComp x />
~~~~~~~
!!! error TS2604: JSX element type 'SFCComp' does not have any construct or call signatures.
~
!!! error TS2322: Type 'true' is not assignable to type 'never'.
!!! related TS6500 tests/cases/conformance/jsx/file.tsx:3:23: The expected type comes from property 'x' which is declared here on type 'IntrinsicAttributes & { x: number; } & { x: boolean; }'

View File

@@ -1,4 +1,4 @@
tests/cases/conformance/jsx/file.tsx(12,2): error TS2604: JSX element type 'SFCComp' does not have any construct or call signatures.
tests/cases/conformance/jsx/file.tsx(12,10): error TS2322: Type 'string' is not assignable to type 'never'.
==== tests/cases/conformance/jsx/file.tsx (1 errors) ====
@@ -14,5 +14,6 @@ tests/cases/conformance/jsx/file.tsx(12,2): error TS2604: JSX element type 'SFCC
var SFCComp = SFC1 || SFC2;
<SFCComp x={"hi"}/>
~~~~~~~
!!! error TS2604: JSX element type 'SFCComp' does not have any construct or call signatures.
~
!!! error TS2322: Type 'string' is not assignable to type 'never'.
!!! related TS6500 tests/cases/conformance/jsx/file.tsx:3:23: The expected type comes from property 'x' which is declared here on type 'IntrinsicAttributes & { x: number; } & { x: boolean; }'

View File

@@ -1,4 +1,5 @@
tests/cases/conformance/jsx/file.tsx(32,10): error TS2604: JSX element type 'RCComp' does not have any construct or call signatures.
tests/cases/conformance/jsx/file.tsx(32,17): error TS2322: Type 'string' is not assignable to type 'number & string'.
Type 'string' is not assignable to type 'number'.
==== tests/cases/conformance/jsx/file.tsx (1 errors) ====
@@ -34,8 +35,10 @@ tests/cases/conformance/jsx/file.tsx(32,10): error TS2604: JSX element type 'RCC
var RCComp = RC1 || RC2;
// OK
let a = <RCComp x="Hi" />;
~~~~~~
!!! error TS2604: JSX element type 'RCComp' does not have any construct or call signatures.
~
!!! error TS2322: Type 'string' is not assignable to type 'number & string'.
!!! error TS2322: Type 'string' is not assignable to type 'number'.
!!! related TS6500 tests/cases/conformance/jsx/file.tsx:3:36: The expected type comes from property 'x' which is declared here on type 'IntrinsicAttributes & IntrinsicClassAttributes<RC1 | RC2> & { x: number; } & { children?: ReactNode; } & { x: string; } & { children?: ReactNode; }'
let a1 = <EmptyRCComp />;
let a2 = <EmptyRCComp data-prop="hello" />;
let b = <PartRCComp />

View File

@@ -1,4 +1,5 @@
tests/cases/conformance/jsx/file.tsx(32,10): error TS2604: JSX element type 'RCComp' does not have any construct or call signatures.
tests/cases/conformance/jsx/file.tsx(32,17): error TS2322: Type 'true' is not assignable to type 'number & string'.
Type 'true' is not assignable to type 'number'.
tests/cases/conformance/jsx/file.tsx(33,10): error TS2322: Type '{ x: number; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<RC4> & { children?: ReactNode; }'.
Property 'x' does not exist on type 'IntrinsicAttributes & IntrinsicClassAttributes<RC4> & { children?: ReactNode; }'.
tests/cases/conformance/jsx/file.tsx(34,10): error TS2322: Type '{ prop: true; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<RC3> & { children?: ReactNode; }'.
@@ -38,8 +39,10 @@ tests/cases/conformance/jsx/file.tsx(34,10): error TS2322: Type '{ prop: true; }
var PartRCComp = RC1 || RC4;
// Error
let a = <RCComp x />;
~~~~~~
!!! error TS2604: JSX element type 'RCComp' does not have any construct or call signatures.
~
!!! error TS2322: Type 'true' is not assignable to type 'number & string'.
!!! error TS2322: Type 'true' is not assignable to type 'number'.
!!! related TS6500 tests/cases/conformance/jsx/file.tsx:3:36: The expected type comes from property 'x' which is declared here on type 'IntrinsicAttributes & IntrinsicClassAttributes<RC1 | RC2> & { x: number; } & { children?: ReactNode; } & { x: string; } & { children?: ReactNode; }'
let b = <PartRCComp x={10} />
~~~~~~~~~~
!!! error TS2322: Type '{ x: number; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<RC4> & { children?: ReactNode; }'.

View File

@@ -2,9 +2,11 @@ tests/cases/conformance/types/union/unionTypeCallSignatures.ts(9,43): error TS23
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(10,29): error TS2345: Argument of type 'true' is not assignable to parameter of type 'string'.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(15,29): error TS2345: Argument of type 'true' is not assignable to parameter of type 'string'.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(16,1): error TS2554: Expected 1 arguments, but got 0.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(19,1): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: number) => number) | ((a: string) => Date)' has no compatible call signatures.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(20,1): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: number) => number) | ((a: string) => Date)' has no compatible call signatures.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(21,1): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: number) => number) | ((a: string) => Date)' has no compatible call signatures.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(19,32): error TS2345: Argument of type '10' is not assignable to parameter of type 'number & string'.
Type '10' is not assignable to type 'string'.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(20,32): error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number & string'.
Type '"hello"' is not assignable to type 'number'.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(21,1): error TS2554: Expected 1 arguments, but got 0.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(24,1): error TS2554: Expected 1 arguments, but got 0.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(26,36): error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number'.
tests/cases/conformance/types/union/unionTypeCallSignatures.ts(29,1): error TS2554: Expected 2 arguments, but got 0.
@@ -56,14 +58,17 @@ tests/cases/conformance/types/union/unionTypeCallSignatures.ts(73,12): error TS2
var unionOfDifferentParameterTypes: { (a: number): number; } | { (a: string): Date; };
unionOfDifferentParameterTypes(10);// error - no call signatures
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: number) => number) | ((a: string) => Date)' has no compatible call signatures.
~~
!!! error TS2345: Argument of type '10' is not assignable to parameter of type 'number & string'.
!!! error TS2345: Type '10' is not assignable to type 'string'.
unionOfDifferentParameterTypes("hello");// error - no call signatures
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: number) => number) | ((a: string) => Date)' has no compatible call signatures.
~~~~~~~
!!! error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number & string'.
!!! error TS2345: Type '"hello"' is not assignable to type 'number'.
unionOfDifferentParameterTypes();// error - no call signatures
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: number) => number) | ((a: string) => Date)' has no compatible call signatures.
!!! error TS2554: Expected 1 arguments, but got 0.
!!! related TS6210 tests/cases/conformance/types/union/unionTypeCallSignatures.ts:18:40: An argument for 'a' was not provided.
var unionOfDifferentNumberOfSignatures: { (a: number): number; } | { (a: number): Date; (a: string): boolean; };
unionOfDifferentNumberOfSignatures(); // error - no call signatures

View File

@@ -2,9 +2,11 @@ tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(9,47): error
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(10,33): error TS2345: Argument of type 'true' is not assignable to parameter of type 'string'.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(15,33): error TS2345: Argument of type 'true' is not assignable to parameter of type 'string'.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(16,1): error TS2554: Expected 1 arguments, but got 0.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(19,1): error TS2351: Cannot use 'new' with an expression whose type lacks a call or construct signature.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(20,1): error TS2351: Cannot use 'new' with an expression whose type lacks a call or construct signature.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(21,1): error TS2351: Cannot use 'new' with an expression whose type lacks a call or construct signature.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(19,36): error TS2345: Argument of type '10' is not assignable to parameter of type 'number & string'.
Type '10' is not assignable to type 'string'.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(20,36): error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number & string'.
Type '"hello"' is not assignable to type 'number'.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(21,1): error TS2554: Expected 1 arguments, but got 0.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(24,1): error TS2554: Expected 1 arguments, but got 0.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(26,40): error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number'.
tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(29,1): error TS2554: Expected 2 arguments, but got 0.
@@ -55,14 +57,17 @@ tests/cases/conformance/types/union/unionTypeConstructSignatures.ts(70,12): erro
var unionOfDifferentParameterTypes: { new (a: number): number; } | { new (a: string): Date; };
new unionOfDifferentParameterTypes(10);// error - no call signatures
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2351: Cannot use 'new' with an expression whose type lacks a call or construct signature.
~~
!!! error TS2345: Argument of type '10' is not assignable to parameter of type 'number & string'.
!!! error TS2345: Type '10' is not assignable to type 'string'.
new unionOfDifferentParameterTypes("hello");// error - no call signatures
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2351: Cannot use 'new' with an expression whose type lacks a call or construct signature.
~~~~~~~
!!! error TS2345: Argument of type '"hello"' is not assignable to parameter of type 'number & string'.
!!! error TS2345: Type '"hello"' is not assignable to type 'number'.
new unionOfDifferentParameterTypes();// error - no call signatures
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2351: Cannot use 'new' with an expression whose type lacks a call or construct signature.
!!! error TS2554: Expected 1 arguments, but got 0.
!!! related TS6210 tests/cases/conformance/types/union/unionTypeConstructSignatures.ts:18:44: An argument for 'a' was not provided.
var unionOfDifferentNumberOfSignatures: { new (a: number): number; } | { new (a: number): Date; new (a: string): boolean; };
new unionOfDifferentNumberOfSignatures(); // error - no call signatures

View File

@@ -1,4 +1,6 @@
tests/cases/conformance/types/union/unionTypeMembers.ts(44,1): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: string) => string) | ((a: number) => number)' has no compatible call signatures.
tests/cases/conformance/types/union/unionTypeMembers.ts(44,38): error TS2345: Argument of type 'string | number' is not assignable to parameter of type 'string & number'.
Type 'string' is not assignable to type 'string & number'.
Type 'string' is not assignable to type 'number'.
tests/cases/conformance/types/union/unionTypeMembers.ts(51,3): error TS2339: Property 'propertyOnlyInI1' does not exist on type 'I1<number> | I2<number>'.
Property 'propertyOnlyInI1' does not exist on type 'I2<number>'.
tests/cases/conformance/types/union/unionTypeMembers.ts(52,3): error TS2339: Property 'propertyOnlyInI2' does not exist on type 'I1<number> | I2<number>'.
@@ -54,8 +56,10 @@ tests/cases/conformance/types/union/unionTypeMembers.ts(54,3): error TS2339: Pro
strOrNum = x.commonMethodDifferentReturnType(str); // string | union
x.commonMethodDifferentParameterType; // No error - property exists
x.commonMethodDifferentParameterType(strOrNum); // error - no call signatures because the type of this property is ((a: string) => string) | (a: number) => number
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type '((a: string) => string) | ((a: number) => number)' has no compatible call signatures.
~~~~~~~~
!!! error TS2345: Argument of type 'string | number' is not assignable to parameter of type 'string & number'.
!!! error TS2345: Type 'string' is not assignable to type 'string & number'.
!!! error TS2345: Type 'string' is not assignable to type 'number'.
// and the call signatures arent identical
num = x.commonMethodWithTypeParameter(num);
num = x.commonMethodWithOwnTypeParameter(num);

View File

@@ -0,0 +1,106 @@
// @jsx: react
// @esModuleInterop: true
// @strict: true
/// <reference path="/.lib/react16.d.ts" />
import React from "react";
// Simple calls from real usecases
function test1() {
type stringType1 = "foo" | "bar";
type stringType2 = "baz" | "bar";
interface Temp1 {
getValue(name: stringType1): number;
}
interface Temp2 {
getValue(name: stringType2): string;
}
function test(t: Temp1 | Temp2) {
const z = t.getValue("bar"); // Should be fine
}
}
function test2() {
interface Messages {
readonly foo: (options: { [key: string]: any, b: number }) => string;
readonly bar: (options: { [key: string]: any, a: string }) => string;
}
const messages: Messages = {
foo: (options) => "Foo",
bar: (options) => "Bar",
};
const test1 = (type: "foo" | "bar") =>
messages[type]({ a: "A", b: 0 });
}
function test3(items: string[] | number[]) {
items.forEach(item => console.log(item));
}
function test4(
arg1: ((...objs: {x: number}[]) => number) | ((...objs: {y: number}[]) => number),
arg2: ((a: {x: number}, b: object) => number) | ((a: object, b: {x: number}) => number),
arg3: ((a: {x: number}, ...objs: {y: number}[]) => number) | ((...objs: {x: number}[]) => number),
arg4: ((a?: {x: number}, b?: {x: number}) => number) | ((a?: {y: number}) => number),
arg5: ((a?: {x: number}, ...b: {x: number}[]) => number) | ((a?: {y: number}) => number),
arg6: ((a?: {x: number}, b?: {x: number}) => number) | ((...a: {y: number}[]) => number),
) {
arg1();
arg1({x: 0, y: 0});
arg1({x: 0, y: 0}, {x: 1, y: 1});
arg2({x: 0}, {x: 0});
arg3({x: 0});
arg3({x: 0}, {x: 0, y: 0});
arg3({x: 0}, {x: 0, y: 0}, {x: 0, y: 0});
arg4();
arg4({x: 0, y: 0});
arg4({x: 0, y: 0}, {x: 0});
arg5();
arg5({x: 0, y: 0});
arg5({x: 0, y: 0}, {x: 0});
arg6();
arg6({x: 0, y: 0});
arg6({x: 0, y: 0}, {x: 0, y: 0});
arg6({x: 0, y: 0}, {x: 0, y: 0}, {y: 0});
}
// JSX Tag names
function test5() {
// Pair of non-like intrinsics
function render(url?: string): React.ReactNode {
const Tag = url ? 'a' : 'button';
return <Tag>test</Tag>;
}
// Union of all intrinsics and components of `any`
function App(props: { component:React.ReactType }) {
const Comp: React.ReactType = props.component;
return (<Comp />);
}
// custom components with non-subset props
function render2() {
interface P1 {
p?: boolean;
c?: string;
}
interface P2 {
p?: boolean;
c?: any;
d?: any;
}
var C: React.ComponentType<P1> | React.ComponentType<P2> = null as any;
const a = <C p={true} />;
}
}

View File

@@ -0,0 +1,53 @@
/// <reference path="fourslash.ts" />
////declare const callableThing1:
//// | ((o1: {x: number}) => void)
//// | ((o1: {y: number}) => void)
//// ;
////
////callableThing1(/*1*/);
////
////declare const callableThing2:
//// | ((o1: {x: number}) => void)
//// | ((o2: {y: number}) => void)
//// ;
////
////callableThing2(/*2*/);
////
////declare const callableThing3:
//// | ((o1: {x: number}) => void)
//// | ((o2: {y: number}) => void)
//// | ((o3: {z: number}) => void)
//// | ((o4: {u: number}) => void)
//// | ((o5: {v: number}) => void)
//// ;
////
////callableThing3(/*3*/);
////
////declare const callableThing4:
//// | ((o1: {x: number}) => void)
//// | ((o2: {y: number}) => void)
//// | ((o3: {z: number}) => void)
//// | ((o4: {u: number}) => void)
//// | ((o5: {v: number}) => void)
//// | ((o6: {w: number}) => void)
//// ;
////
////callableThing4(/*4*/);
verify.signatureHelp({
marker: "1",
text: "callableThing1(o1: { x: number; } & { y: number; }): void"
},
{
marker: "2",
text: "callableThing2(arg0: { x: number; } & { y: number; }): void"
},
{
marker: "3",
text: "callableThing3(arg0: { x: number; } & { y: number; } & { z: number; } & { u: number; } & { v: number; }): void"
},
{
marker: "4",
text: "callableThing4(arg0: { x: number; } & { y: number; } & { z: number; } & { u: number; } & { v: number; } & { w: number; }): void"
});

View File

@@ -19,4 +19,4 @@
//// var SFCComp = SFC1 || SFC2;
//// <SFCComp /**/ />
verify.completions({ marker: "", exact: undefined });
verify.completions({ marker: "", exact: ["x"] });

View File

@@ -22,5 +22,5 @@
//// <[|SFC/*one*/Comp|] x />
verify.goToDefinition({
"one": ["def"],
"one": ["def", "pt1"],
});