如何使用打字稿在 React 中将对象作为道具传递?

时间:2021-07-05 05:41:21

标签: reactjs typescript react-props react-typescript

我正在努力学习打字稿,老实说,我有很多时间都在思考这个问题。我知道这个问题之前已经被问过无数次,但我一生都无法弄清楚如何将我正在阅读的答案翻译成我自己的代码。没有帮助的是很多答案,我似乎发现使用与我一直使用不同的语法来编写组件。无论如何,非常感谢任何帮助,因为我在这里完全迷失了。我实际上只有两个文件,App.tsx 和 DisplayPerson.tsx

在我的 App.tsx 文件中,我有这个代码:

import React from 'react';
import DisplayPerson from './components/DisplayPerson';

export interface Person {
    firstName: string;
    lastName: string;
}

function App() {
    const person1: Person = {
        firstName: 'fname',
        lastName: 'lname',
    };

    return (
        <div>
            <DisplayPerson person={person1} />
        </div>
    );
}

export default App;

在我的 DisplayPerson.tsx 文件中,我有:

import React from 'react';
import { Person } from '../App';

export default function DisplayPerson({ person }: Person) {
    return (
        <div>
            <h1>person.firstName</h1>
            <h1>person.lastName</h1>
        </div>
    );
}

在 DisplayPerson.tsx 中,我有一个错误,显示“类型 'Person' 上不存在属性 'person'”。我试图通过将我的 Person 界面更改为:

来解决此问题
export interface Person {
    person : {
        firstName: string;
        lastName: string;
    }
}

我的 person1 const 声明如下:

const person1: Person = {
        person: {
            firstName: 'fname',
            lastName: 'lname',
        },
    };

这确实解决了 DisplayPerson.tsx 中的错误,但是我现在在 App.tsx 中出现错误,提示“类型‘人’缺少类型‘{ firstName: string; lastName: string;}’中的以下属性: firstName, lastName。预期的类型来自属性“person”,该属性在此处声明为类型“IntrinsicAttributes & Person”

这是我尝试使用谷歌搜索我的问题的时候,坦率地说,即使不使用谷歌搜索,我也无法弄清楚出了什么问题。非常感谢任何帮助,如果您也能解释为什么我所做的不起作用,我会非常喜欢。

非常感谢!

3 个答案:

答案 0 :(得分:3)

我认为您在 DisplayPerson.tsx 中有几个小问题。我已经在这个代码和框中修复了它们:https://codesandbox.io/s/modest-snyder-s5bmt?file=/src/App.tsx

DisplayPerson.tsx

import React from 'react';
import { Person } from '../App';

export default function DisplayPerson({ person }: { person: Person }) {
    return (
        <div>
            <h1>{person.firstName}</h1>
            <h1>{person.lastName}</h1>
        </div>
    );
}
  1. 您的道具类型不正确。您应该使用 { person }: Person 而不是 { person }: { person: Person }
  2. 你应该用 person.firstName 包裹 person.lastName{}

详细说明#1:传入 DisplayPerson 的 props 是一个对象,其中键是 prop 名称,值是传入的任何内容。因此,props 对象的类型不是 {{1 }} 而是具有键 Person 和类型为 person 的值的对象。

答案 1 :(得分:2)

您需要更正道具部分。所以你的 DisplayPerson.tsx 文件会是这样的

import React from 'react';
import { Person } from '../App';

interface IProps {
   person: Person
}
export default function DisplayPerson({ person }: IProps) {
    return (
        <div>
            <h1>{person.firstName}</h1>
            <h1>{person.lastName}</h1>
        </div>
    );
}

更新:

在 React 中,函数式组件的结构如下

function DisplayPerson(props) {}

正如您在此处看到的,props 是一个类型为 object 的参数。所以你需要传递一个 object。现在你想要一个 person 作为对象内部的 key 对象解构。 这就是为什么它必须像 Nathan 的回答中的 #1 那样完成。
你可以参考这个:https://javascript.info/destructuring-assignment#object-destructuring

答案 2 :(得分:1)

我发现了问题,您没有将参数作为道具传递。你必须这样做,我已经解决了:

App.tsx

import React from 'react';
import DisplayPerson from './components/DisplayPerson';

export interface Person {
    firstName: string;
    lastName: string;
}

function App() {
    const person1: Person = {
        firstName: 'fname',
        lastName: 'lname',
    };

    return (
        <div>
            <DisplayPerson person={person1} />
        </div>
    );
}

export default App;

DisplayPerson.tsx

import React from 'react';
import { Person } from '../App';

export default function DisplayPerson(props:{person:Person}) {
    return (
        <div>
            <h1>props.person.firstName</h1>
            <h1>props.person.lastName</h1>
        </div>
    );
}