使用TypeScript在useState React Hook上设置类型

hta*_*irt 27 typescript reactjs react-hooks

我正在使用TypeScript项目迁移React以使用钩子功能(React v16.7.0-alpha),但我无法弄清楚如何设置析构元素的类型.

这是一个例子:

interface IUser {
  name: string;
}
...
const [user, setUser] = useState({name: 'Jon'});
Run Code Online (Sandbox Code Playgroud)

我想强制user变量为类型IUser.我唯一成功的试验是分两个阶段进行:打字,然后初始化:

let user: IUser;
let setUser: any;
[user, setUser] = useState({name: 'Jon'});
Run Code Online (Sandbox Code Playgroud)

但我确信有更好的方法.此外,setUser应该初始化为一个带有IUser输入的函数,并且不返回任何内容.

另外,值得注意的是,const [user, setUser] = useState({name: 'Jon'});没有任何初始化的使用工作正常,但我想利用TypeScript强制在init上进行类型检查,特别是如果它依赖于一些道具.

谢谢你的帮助.

Nur*_*yev 54

用这个

const [user, setUser] = useState<IUser>({name: 'Jon'});
Run Code Online (Sandbox Code Playgroud)

请在此处查看相应的类型:https://github.com/DefinitelyTyped/DefinitelyTyped/blob/master/types/react/index.d.ts#L799

  • @orome不,你不能在那里放任何东西,你只能在那里放一个与“IUser”兼容的对象,即具有相同的属性。这就是所谓的鸭子打字。 (3认同)
  • 在过去的6个月中,我已提及此答案约6次 (2认同)
  • @JoãoMarcosGris `类型 MyType = MyObj[]; ` 然后 `useState&lt;MyType&gt;` (2认同)
  • @JoeyBaruch 不,我们不是:-) 试试吧。然后查看类型定义,你会发现 `useState` 返回一个类型良好的元组,它被分配给 `[user, setUser]` 并且 TypeScript 不难理解变量应该是相同的类型作为元组成分。不知道我是否澄清了事情或使您进一步困惑。 (2认同)

cha*_*ham 28

首先useState需要一个泛型,这将是您的 IUser。如果您想传递由useState您返回的第二个解构元素,则需要导入 Dispatch。考虑您的示例的这个扩展版本,它有一个点击处理程序:

import React, { useState, Dispatch } from 'react';

interface IUser {
  name: string;
}

export const yourComponent = (setUser: Dispatch<IUser>) => {

    const [user, setUser] = useState<IUser>({name: 'Jon'});

    const clickHander = (stateSetter: Dispatch<IUser>) => {
        stateSetter({name : 'Jane'});
    }

    return (
         <div>
            <button onClick={() => { clickHander(setUser) }}>Change Name</button>
        </div>
    ) 
}
Run Code Online (Sandbox Code Playgroud)

看到这个答案