lgq*_*lgq 6 typescript reactjs
正如标题所说,我有一个像这样的反应FC:
const Test = (props: {
children: React.ReactElement<{ slot: "content" }>
}) => {
return <></>
}
Run Code Online (Sandbox Code Playgroud)
现在,传递一个没有 slot 属性的子元素,没有任何 ts 错误
const test = (
<Test>
<span>some content</span>
</Test>
)
Run Code Online (Sandbox Code Playgroud)
我知道 span 标签将被推断为 JSX.Element,但是有什么方法可以让我收到 ts 错误,指出 span 没有 slot 属性
不,这是不可能的:
“JSX 结果类型”:
默认情况下,JSX 表达式的结果类型为
any. 您可以通过指定接口来自定义类型JSX.Element。但是,无法从此接口检索有关 JSX 的元素、属性或子级的类型信息。它是一个黑匣子。
JSX 代码(如<span>some content</span>)始终被解释为类型JSX.Element(如您所说)。
JSX.Element定义为:
declare global {
namespace JSX {
interface Element extends React.ReactElement<any, any> {}
}
}
Run Code Online (Sandbox Code Playgroud)
any根据定义可分配给任何类型(并且任何类型都可以分配给它)。
因此,没有办法限制组件内部的任何内容,因为没有关于传入内容的信息,它只是any.
您不必限制传入的类型,而是必须JSX.Element以某种方式覆盖创建的类型(但这也不起作用):
declare global {
namespace JSX {
interface Element<K, V> extends React.ReactElement<K, V> {} // <-- doesn't work
}
}
Run Code Online (Sandbox Code Playgroud)
...所以K并且V是从 JSX 代码推断出来的。
但 TypeScript 无法从 JSX 代码推断类型。
TS 本身甚至不知道 JSX 代码应该编译成什么,您必须配置 TS,以便它编译以创建 React 元素(通常已经预先定义)。但是您也可以将 JSX 代码编译为完全不同的代码,或者根本不编译(即,仅将 JSX 代码不变地传递)。(例如 tsconfig.json 选项jsx或jsxFactory)
此外,TS 扫描源代码并应用/推断所有类型,然后创建 JS 代码(不含类型)并将 JSX 转换为 JS。
现在,我认为开发一个从 JSX 代码推断类型的系统在技术上是可能的,但这需要付出相当大的努力。例如:
key和children是特殊的?| 归档时间: |
|
| 查看次数: |
125 次 |
| 最近记录: |