From 0faf32b27949e06739f6a41ad64922af1bc949e7 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders Date: Thu, 13 Oct 2016 09:27:20 -0700 Subject: [PATCH 1/3] Add spread syntax to JsxExpression. This allows you to specify that a JsxExpression should be a list that will be flattened by the JSX consumer. --- src/compiler/checker.ts | 6 +++++- src/compiler/diagnosticMessages.json | 4 ++++ src/compiler/emitter.ts | 3 +++ src/compiler/factory.ts | 7 ++++--- src/compiler/parser.ts | 4 +++- src/compiler/types.ts | 1 + 6 files changed, 20 insertions(+), 5 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index a1a8ae0da5c07..db318e4eb177d 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10904,7 +10904,11 @@ namespace ts { function checkJsxExpression(node: JsxExpression) { if (node.expression) { - return checkExpression(node.expression); + const type = checkExpression(node.expression); + if (node.dotDotDotToken && !isArrayType(type)) { + error(node, Diagnostics.JSX_spread_child_must_be_an_array_type, node.toString(), typeToString(type)); + } + return type; } else { return unknownType; diff --git a/src/compiler/diagnosticMessages.json b/src/compiler/diagnosticMessages.json index 1b8c995ea057f..f0ccc7f33e2cd 100644 --- a/src/compiler/diagnosticMessages.json +++ b/src/compiler/diagnosticMessages.json @@ -1787,6 +1787,10 @@ "category": "Error", "code": 2608 }, + "JSX spread child must be an array type.": { + "category": "Error", + "code": 2609 + }, "Cannot emit namespaced JSX elements in React": { "category": "Error", "code": 2650 diff --git a/src/compiler/emitter.ts b/src/compiler/emitter.ts index 270fb0ca62469..dae75e2516cde 100644 --- a/src/compiler/emitter.ts +++ b/src/compiler/emitter.ts @@ -1969,6 +1969,9 @@ const _super = (function (geti, seti) { function emitJsxExpression(node: JsxExpression) { if (node.expression) { write("{"); + if (node.dotDotDotToken) { + write("..."); + } emitExpression(node.expression); write("}"); } diff --git a/src/compiler/factory.ts b/src/compiler/factory.ts index 97a36f46b1341..d050739470fb0 100644 --- a/src/compiler/factory.ts +++ b/src/compiler/factory.ts @@ -1318,15 +1318,16 @@ namespace ts { return node; } - export function createJsxExpression(expression: Expression, location?: TextRange) { + export function createJsxExpression(expression: Expression, dotDotDotToken: Token, location?: TextRange) { const node = createNode(SyntaxKind.JsxExpression, location); + node.dotDotDotToken = dotDotDotToken; node.expression = expression; return node; } export function updateJsxExpression(node: JsxExpression, expression: Expression) { if (node.expression !== expression) { - return updateNode(createJsxExpression(expression, node), node); + return updateNode(createJsxExpression(expression, node.dotDotDotToken, node), node); } return node; } @@ -2910,4 +2911,4 @@ namespace ts { function tryGetModuleNameFromDeclaration(declaration: ImportEqualsDeclaration | ImportDeclaration | ExportDeclaration, host: EmitHost, resolver: EmitResolver, compilerOptions: CompilerOptions) { return tryGetModuleNameFromFile(resolver.getExternalModuleFileFromDeclaration(declaration), host, compilerOptions); } -} \ No newline at end of file +} diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 62ae61e4cb432..1133a5bafd682 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -362,7 +362,8 @@ namespace ts { case SyntaxKind.JsxSpreadAttribute: return visitNode(cbNode, (node).expression); case SyntaxKind.JsxExpression: - return visitNode(cbNode, (node).expression); + return visitNode(cbNode, (node as JsxExpression).dotDotDotToken) || + visitNode(cbNode, (node as JsxExpression).expression); case SyntaxKind.JsxClosingElement: return visitNode(cbNode, (node).tagName); @@ -3821,6 +3822,7 @@ namespace ts { parseExpected(SyntaxKind.OpenBraceToken); if (token() !== SyntaxKind.CloseBraceToken) { + node.dotDotDotToken = parseOptionalToken(SyntaxKind.DotDotDotToken); node.expression = parseAssignmentExpressionOrHigher(); } if (inExpressionContext) { diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 638504e613f11..e54157ba98696 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -1396,6 +1396,7 @@ namespace ts { export interface JsxExpression extends Expression { kind: SyntaxKind.JsxExpression; + dotDotDotToken?: Token; expression?: Expression; } From d29c78e7189fcbcc13bd54f88d52948ddf65ff9f Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders Date: Thu, 13 Oct 2016 09:28:39 -0700 Subject: [PATCH 2/3] Add spread syntax tests for JsxExpressions And baselines --- .../baselines/reference/tsxSpreadChildren.js | 41 ++++++++ .../reference/tsxSpreadChildren.symbols | 86 +++++++++++++++++ .../reference/tsxSpreadChildren.types | 94 +++++++++++++++++++ .../tsxSpreadChildrenInvalidType.errors.txt | 32 +++++++ .../reference/tsxSpreadChildrenInvalidType.js | 46 +++++++++ .../conformance/jsx/tsxSpreadChildren.tsx | 27 ++++++ .../jsx/tsxSpreadChildrenInvalidType.tsx | 26 +++++ 7 files changed, 352 insertions(+) create mode 100644 tests/baselines/reference/tsxSpreadChildren.js create mode 100644 tests/baselines/reference/tsxSpreadChildren.symbols create mode 100644 tests/baselines/reference/tsxSpreadChildren.types create mode 100644 tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt create mode 100644 tests/baselines/reference/tsxSpreadChildrenInvalidType.js create mode 100644 tests/cases/conformance/jsx/tsxSpreadChildren.tsx create mode 100644 tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx diff --git a/tests/baselines/reference/tsxSpreadChildren.js b/tests/baselines/reference/tsxSpreadChildren.js new file mode 100644 index 0000000000000..bcc62de056670 --- /dev/null +++ b/tests/baselines/reference/tsxSpreadChildren.js @@ -0,0 +1,41 @@ +//// [tsxSpreadChildren.tsx] + +declare module JSX { + interface Element { } + interface IntrinsicElements { + [s: string]: any; + } +} +declare var React: any; + +interface TodoProp { + id: number; + todo: string; +} +interface TodoListProps { + todos: TodoProp[]; +} +function Todo(prop: { key: number, todo: string }) { + return
{prop.key.toString() + prop.todo}
; +} +function TodoList({ todos }: TodoListProps) { + return
+ {...todos.map(todo => )} +
; +} +let x: TodoListProps; + + + +//// [tsxSpreadChildren.jsx] +function Todo(prop) { + return
{prop.key.toString() + prop.todo}
; +} +function TodoList(_a) { + var todos = _a.todos; + return
+ {...todos.map(function (todo) { return ; })} +
; +} +var x; +; diff --git a/tests/baselines/reference/tsxSpreadChildren.symbols b/tests/baselines/reference/tsxSpreadChildren.symbols new file mode 100644 index 0000000000000..6e726e932179b --- /dev/null +++ b/tests/baselines/reference/tsxSpreadChildren.symbols @@ -0,0 +1,86 @@ +=== tests/cases/conformance/jsx/tsxSpreadChildren.tsx === + +declare module JSX { +>JSX : Symbol(JSX, Decl(tsxSpreadChildren.tsx, 0, 0)) + + interface Element { } +>Element : Symbol(Element, Decl(tsxSpreadChildren.tsx, 1, 20)) + + interface IntrinsicElements { +>IntrinsicElements : Symbol(IntrinsicElements, Decl(tsxSpreadChildren.tsx, 2, 22)) + + [s: string]: any; +>s : Symbol(s, Decl(tsxSpreadChildren.tsx, 4, 3)) + } +} +declare var React: any; +>React : Symbol(React, Decl(tsxSpreadChildren.tsx, 7, 11)) + +interface TodoProp { +>TodoProp : Symbol(TodoProp, Decl(tsxSpreadChildren.tsx, 7, 23)) + + id: number; +>id : Symbol(TodoProp.id, Decl(tsxSpreadChildren.tsx, 9, 20)) + + todo: string; +>todo : Symbol(TodoProp.todo, Decl(tsxSpreadChildren.tsx, 10, 15)) +} +interface TodoListProps { +>TodoListProps : Symbol(TodoListProps, Decl(tsxSpreadChildren.tsx, 12, 1)) + + todos: TodoProp[]; +>todos : Symbol(TodoListProps.todos, Decl(tsxSpreadChildren.tsx, 13, 25)) +>TodoProp : Symbol(TodoProp, Decl(tsxSpreadChildren.tsx, 7, 23)) +} +function Todo(prop: { key: number, todo: string }) { +>Todo : Symbol(Todo, Decl(tsxSpreadChildren.tsx, 15, 1)) +>prop : Symbol(prop, Decl(tsxSpreadChildren.tsx, 16, 14)) +>key : Symbol(key, Decl(tsxSpreadChildren.tsx, 16, 21)) +>todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 16, 34)) + + return
{prop.key.toString() + prop.todo}
; +>div : Symbol(JSX.IntrinsicElements, Decl(tsxSpreadChildren.tsx, 2, 22)) +>prop.key.toString : Symbol(Number.toString, Decl(lib.d.ts, --, --)) +>prop.key : Symbol(key, Decl(tsxSpreadChildren.tsx, 16, 21)) +>prop : Symbol(prop, Decl(tsxSpreadChildren.tsx, 16, 14)) +>key : Symbol(key, Decl(tsxSpreadChildren.tsx, 16, 21)) +>toString : Symbol(Number.toString, Decl(lib.d.ts, --, --)) +>prop.todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 16, 34)) +>prop : Symbol(prop, Decl(tsxSpreadChildren.tsx, 16, 14)) +>todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 16, 34)) +>div : Symbol(JSX.IntrinsicElements, Decl(tsxSpreadChildren.tsx, 2, 22)) +} +function TodoList({ todos }: TodoListProps) { +>TodoList : Symbol(TodoList, Decl(tsxSpreadChildren.tsx, 18, 1)) +>todos : Symbol(todos, Decl(tsxSpreadChildren.tsx, 19, 19)) +>TodoListProps : Symbol(TodoListProps, Decl(tsxSpreadChildren.tsx, 12, 1)) + + return
+>div : Symbol(JSX.IntrinsicElements, Decl(tsxSpreadChildren.tsx, 2, 22)) + + {...todos.map(todo => )} +>todos.map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>todos : Symbol(todos, Decl(tsxSpreadChildren.tsx, 19, 19)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 21, 22)) +>Todo : Symbol(Todo, Decl(tsxSpreadChildren.tsx, 15, 1)) +>key : Symbol(key, Decl(tsxSpreadChildren.tsx, 16, 21)) +>todo.id : Symbol(TodoProp.id, Decl(tsxSpreadChildren.tsx, 9, 20)) +>todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 21, 22)) +>id : Symbol(TodoProp.id, Decl(tsxSpreadChildren.tsx, 9, 20)) +>todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 16, 34)) +>todo.todo : Symbol(TodoProp.todo, Decl(tsxSpreadChildren.tsx, 10, 15)) +>todo : Symbol(todo, Decl(tsxSpreadChildren.tsx, 21, 22)) +>todo : Symbol(TodoProp.todo, Decl(tsxSpreadChildren.tsx, 10, 15)) + +
; +>div : Symbol(JSX.IntrinsicElements, Decl(tsxSpreadChildren.tsx, 2, 22)) +} +let x: TodoListProps; +>x : Symbol(x, Decl(tsxSpreadChildren.tsx, 24, 3)) +>TodoListProps : Symbol(TodoListProps, Decl(tsxSpreadChildren.tsx, 12, 1)) + + +>TodoList : Symbol(TodoList, Decl(tsxSpreadChildren.tsx, 18, 1)) +>x : Symbol(x, Decl(tsxSpreadChildren.tsx, 24, 3)) + diff --git a/tests/baselines/reference/tsxSpreadChildren.types b/tests/baselines/reference/tsxSpreadChildren.types new file mode 100644 index 0000000000000..fbf76d0679d18 --- /dev/null +++ b/tests/baselines/reference/tsxSpreadChildren.types @@ -0,0 +1,94 @@ +=== tests/cases/conformance/jsx/tsxSpreadChildren.tsx === + +declare module JSX { +>JSX : any + + interface Element { } +>Element : Element + + interface IntrinsicElements { +>IntrinsicElements : IntrinsicElements + + [s: string]: any; +>s : string + } +} +declare var React: any; +>React : any + +interface TodoProp { +>TodoProp : TodoProp + + id: number; +>id : number + + todo: string; +>todo : string +} +interface TodoListProps { +>TodoListProps : TodoListProps + + todos: TodoProp[]; +>todos : TodoProp[] +>TodoProp : TodoProp +} +function Todo(prop: { key: number, todo: string }) { +>Todo : (prop: { key: number; todo: string; }) => JSX.Element +>prop : { key: number; todo: string; } +>key : number +>todo : string + + return
{prop.key.toString() + prop.todo}
; +>
{prop.key.toString() + prop.todo}
: JSX.Element +>div : any +>prop.key.toString() + prop.todo : string +>prop.key.toString() : string +>prop.key.toString : (radix?: number) => string +>prop.key : number +>prop : { key: number; todo: string; } +>key : number +>toString : (radix?: number) => string +>prop.todo : string +>prop : { key: number; todo: string; } +>todo : string +>div : any +} +function TodoList({ todos }: TodoListProps) { +>TodoList : ({todos}: TodoListProps) => JSX.Element +>todos : TodoProp[] +>TodoListProps : TodoListProps + + return
+>
{...todos.map(todo => )}
: JSX.Element +>div : any + + {...todos.map(todo => )} +>todos.map(todo => ) : JSX.Element[] +>todos.map : { (this: [TodoProp, TodoProp, TodoProp, TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U, U, U, U]; (this: [TodoProp, TodoProp, TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U, U, U]; (this: [TodoProp, TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U, U]; (this: [TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U]; (callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): U[]; } +>todos : TodoProp[] +>map : { (this: [TodoProp, TodoProp, TodoProp, TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U, U, U, U]; (this: [TodoProp, TodoProp, TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U, U, U]; (this: [TodoProp, TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U, U]; (this: [TodoProp, TodoProp], callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): [U, U]; (callbackfn: (value: TodoProp, index: number, array: TodoProp[]) => U, thisArg?: any): U[]; } +>todo => : (todo: TodoProp) => JSX.Element +>todo : TodoProp +> : JSX.Element +>Todo : (prop: { key: number; todo: string; }) => JSX.Element +>key : any +>todo.id : number +>todo : TodoProp +>id : number +>todo : any +>todo.todo : string +>todo : TodoProp +>todo : string + +
; +>div : any +} +let x: TodoListProps; +>x : TodoListProps +>TodoListProps : TodoListProps + + +> : JSX.Element +>TodoList : ({todos}: TodoListProps) => JSX.Element +>x : TodoListProps + diff --git a/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt b/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt new file mode 100644 index 0000000000000..d052654167313 --- /dev/null +++ b/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt @@ -0,0 +1,32 @@ +tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx(21,9): error TS2609: JSX spread child must be an array type. + + +==== tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx (1 errors) ==== + declare module JSX { + interface Element { } + interface IntrinsicElements { + [s: string]: any; + } + } + declare var React: any; + + interface TodoProp { + id: number; + todo: string; + } + interface TodoListProps { + todos: TodoProp[]; + } + function Todo(prop: { key: number, todo: string }) { + return
{prop.key.toString() + prop.todo}
; + } + function TodoList({ todos }: TodoListProps) { + return
+ {...} + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +!!! error TS2609: JSX spread child must be an array type. +
; + } + let x: TodoListProps; + + \ No newline at end of file diff --git a/tests/baselines/reference/tsxSpreadChildrenInvalidType.js b/tests/baselines/reference/tsxSpreadChildrenInvalidType.js new file mode 100644 index 0000000000000..507b36665d562 --- /dev/null +++ b/tests/baselines/reference/tsxSpreadChildrenInvalidType.js @@ -0,0 +1,46 @@ +//// [tsxSpreadChildrenInvalidType.tsx] +declare module JSX { + interface Element { } + interface IntrinsicElements { + [s: string]: any; + } +} +declare var React: any; + +interface TodoProp { + id: number; + todo: string; +} +interface TodoListProps { + todos: TodoProp[]; +} +function Todo(prop: { key: number, todo: string }) { + return
{prop.key.toString() + prop.todo}
; +} +function TodoList({ todos }: TodoListProps) { + return
+ {...} +
; +} +let x: TodoListProps; + + + +//// [tsxSpreadChildrenInvalidType.js] +var __assign = (this && this.__assign) || Object.assign || function(t) { + for (var s, i = 1, n = arguments.length; i < n; i++) { + s = arguments[i]; + for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) + t[p] = s[p]; + } + return t; +}; +function Todo(prop) { + return React.createElement("div", null, prop.key.toString() + prop.todo); +} +function TodoList(_a) { + var todos = _a.todos; + return React.createElement("div", null, React.createElement(Todo, { key: todos[0].id, todo: todos[0].todo })); +} +var x; +React.createElement(TodoList, __assign({}, x)); diff --git a/tests/cases/conformance/jsx/tsxSpreadChildren.tsx b/tests/cases/conformance/jsx/tsxSpreadChildren.tsx new file mode 100644 index 0000000000000..3be0b3b99e459 --- /dev/null +++ b/tests/cases/conformance/jsx/tsxSpreadChildren.tsx @@ -0,0 +1,27 @@ +//@jsx: preserve + +declare module JSX { + interface Element { } + interface IntrinsicElements { + [s: string]: any; + } +} +declare var React: any; + +interface TodoProp { + id: number; + todo: string; +} +interface TodoListProps { + todos: TodoProp[]; +} +function Todo(prop: { key: number, todo: string }) { + return
{prop.key.toString() + prop.todo}
; +} +function TodoList({ todos }: TodoListProps) { + return
+ {...todos.map(todo => )} +
; +} +let x: TodoListProps; + diff --git a/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx b/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx new file mode 100644 index 0000000000000..20f7d4fae873d --- /dev/null +++ b/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx @@ -0,0 +1,26 @@ +// @jsx: react +declare module JSX { + interface Element { } + interface IntrinsicElements { + [s: string]: any; + } +} +declare var React: any; + +interface TodoProp { + id: number; + todo: string; +} +interface TodoListProps { + todos: TodoProp[]; +} +function Todo(prop: { key: number, todo: string }) { + return
{prop.key.toString() + prop.todo}
; +} +function TodoList({ todos }: TodoListProps) { + return
+ {...} +
; +} +let x: TodoListProps; + From 7eb39cc80ce7725afacb1b75763fd7fcd505d964 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders Date: Thu, 13 Oct 2016 10:17:01 -0700 Subject: [PATCH 3/3] Allow any type for spreads in JsxExpression --- src/compiler/checker.ts | 2 +- .../reference/tsxSpreadChildrenInvalidType.errors.txt | 6 ++++++ .../reference/tsxSpreadChildrenInvalidType.js | 11 +++++++++++ .../conformance/jsx/tsxSpreadChildrenInvalidType.tsx | 6 ++++++ 4 files changed, 24 insertions(+), 1 deletion(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index db318e4eb177d..78481c17d1f96 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10905,7 +10905,7 @@ namespace ts { function checkJsxExpression(node: JsxExpression) { if (node.expression) { const type = checkExpression(node.expression); - if (node.dotDotDotToken && !isArrayType(type)) { + if (node.dotDotDotToken && type !== anyType && !isArrayType(type)) { error(node, Diagnostics.JSX_spread_child_must_be_an_array_type, node.toString(), typeToString(type)); } return type; diff --git a/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt b/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt index d052654167313..d1524c6bf3a97 100644 --- a/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt +++ b/tests/baselines/reference/tsxSpreadChildrenInvalidType.errors.txt @@ -27,6 +27,12 @@ tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx(21,9): error TS2609 !!! error TS2609: JSX spread child must be an array type. ; } + function TodoListNoError({ todos }: TodoListProps) { + // any is not checked + return
+ {...( as any)} +
; + } let x: TodoListProps; \ No newline at end of file diff --git a/tests/baselines/reference/tsxSpreadChildrenInvalidType.js b/tests/baselines/reference/tsxSpreadChildrenInvalidType.js index 507b36665d562..e9873bfb233a6 100644 --- a/tests/baselines/reference/tsxSpreadChildrenInvalidType.js +++ b/tests/baselines/reference/tsxSpreadChildrenInvalidType.js @@ -22,6 +22,12 @@ function TodoList({ todos }: TodoListProps) { {...} ; } +function TodoListNoError({ todos }: TodoListProps) { + // any is not checked + return
+ {...( as any)} +
; +} let x: TodoListProps; @@ -42,5 +48,10 @@ function TodoList(_a) { var todos = _a.todos; return React.createElement("div", null, React.createElement(Todo, { key: todos[0].id, todo: todos[0].todo })); } +function TodoListNoError(_a) { + var todos = _a.todos; + // any is not checked + return React.createElement("div", null, React.createElement(Todo, { key: todos[0].id, todo: todos[0].todo })); +} var x; React.createElement(TodoList, __assign({}, x)); diff --git a/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx b/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx index 20f7d4fae873d..41181618ce0a3 100644 --- a/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx +++ b/tests/cases/conformance/jsx/tsxSpreadChildrenInvalidType.tsx @@ -22,5 +22,11 @@ function TodoList({ todos }: TodoListProps) { {...} ; } +function TodoListNoError({ todos }: TodoListProps) { + // any is not checked + return
+ {...( as any)} +
; +} let x: TodoListProps;