React:我有一个呈现用户数据的组件,如果呈现数据出错,我想在该部分下方显示一条错误消息

React: I have a component that renders user data and I want to display an error message underneath the section if there's an error rendering the data

我有一个部分组件可以获取用户数据,然后在 3 个单独的 headers 下显示该数据。如果数据获取失败,我想添加一个单独的渲染器,它会在 headers 下方显示一条错误消息,我不太确定这样做的最佳做法是什么。我有我的组件和服务来获取下面列出的数据,有什么建议吗?

User Info Component
import React from 'react'
import PropTypes from 'prop-types'
import styled from 'styled-components'
import {
  Col,
  Row,
  Input,
  Checkbox
} from 'antd'


const CustomerDetails = ({ customer }) =>
  !!Object.keys(customer).length && (
    <Container>
      <h2>
        {/* Name */}
        Test Test
      </h2>
      <Row>
        <Col span={8}>
          <Ul>
            <h3><strong>Primary Contact</strong></h3>
            <li>Jane Doe</li>
            <li>212-333-3333</li>
          </Ul>
        </Col>
        <Col span={8}>
          <Ul>
            <h3><strong>Service Address</strong></h3>
            <li>1234 Stone Ave N</li>
            <li>STE FR6</li>
            <li>Seattle, WA 12345</li>
          </Ul>
        </Col>
        <Col span={8}>
          <Ul>
            <h3><strong>Billing Address</strong></h3>
            <li>1234 Stone Ave N</li>
            <li>STE FR6</li>
            <li>Seattle, WA 12345</li>
          </Ul>
        </Col>
      </Row>
      <br />
      <Row>
        <Col span={10}>
          <h4>PRIMARY CONTACT EMAIL</h4>
        </Col>
      </Row>
      <Row>
        <Col span={8}>
          <StyledInput />
        </Col>
        <Col span={12}>
          <StyledCheckbox /> EMAIL OPT OUT
        </Col>
      </Row>
      <br />
      <Row>
        <Col>
          <StyledCheckbox /> TAX EXEMPT
        </Col>
      </Row>
      <br />
      <Row>
        <Col>
          <h4>GO TO BUNDLE BUILDER</h4>
        </Col>
      </Row>
    </Container>
  )

CustomerDetails.propTypes = {
  customer: PropTypes.object
}

CustomerDetails.defaultProps = {
  customer: {}
}

const Container = styled.div`
  margin: 15px 5px;
`
const StyledCheckbox = styled(Checkbox)`

`
const StyledInput = styled(Input)`
  max-width: 75%;
`
const Ul = styled.ul`
  list-style-type: none;

  li {
    font-size: 1rem;
  }
`

export default CustomerDetails
API service to fetch user data
import Axios from 'axios'
import { logError } from './logging'

export async function getCustomer(customer = {}) {
  try {
    const { customerId } = customer
    console.info('Customer ID:', customerId)

    const { data } = await Axios.get('https://getUserInfoAPI.com')

    return new Promise(res => {
      setTimeout(() => res(data), 3000)
    })
  } catch (error) {
    logError(error)
    throw error
  }
}

How/Where 您是在进行 API 调用并将其传递给您的组件吗? React 有一个新的钩子 api 可以让你使用 function-based 组件来做大多数事情,但听起来你对 React 还很陌生,class 和函数组件之间的二分法可能会有所帮助在您开始时为您服务。现在,这样想:

  • 功能组件:愚蠢。只获取数据并呈现它。
  • ClassCompoennts(或带钩子的函数组件):渲染数据,但也有自己的状态和生命周期方法

所以我相信您已经意识到,拥有一种获取数据和呈现数据的方式不仅很重要,而且拥有一种管理状态的方式也很重要。例如,您想要一个可以存储数据并在以后访问的地方,或者可能像 "loading" (t/f) 或 "error" (t/f) 这样的状态信息。

另一个有用的概念是组件组合。我们将利用一个更高阶的组件,它现在处理 API 调用(有更复杂的解决方案,带有 redux / redux-sagas 等库),并有条件地显示 table,或者否则一条错误消息。

class MyComponent extends react.Component {
  constructor(props){
    super(props);
    this.state = {
      loading: false,
      error: false,
      data: {}
    }
  }

  //this is just a utility function so that you can use async / await with setState
  setStateAsync(state) {
    return new Promise((resolve) => {
      this.setState(state, resolve)
    });
  }

  //will run after your component is mounted to the dom
  async componentDidMount() {
    try{
      await this.setStateAsync({...this.state, loading: true})
      let data = await getCustomer();
      await this.setStateAsync({...this.state, loading: false, data})
    } catch(e) {
      this.setState({error: true, loading: false, data: {}})
    }
  }

  //stick what you would normally return in a function component here
  render() {
    return (
      {this.state.loading ? (<div>"...loading"</div>) :
         this.state.error ? (<div style={{color: 'red'}}>ERROR!</div> :
         (<CustomerDetails customer={this.state.data} />)
    )
  }
}

通读 this 以获取有关 class 组件的更多信息。上面的示例非常简单,但请注意:

  1. 有本地状态
  2. 组件根据道具和本地状态呈现
  3. return 语句将 javascript 包装在 {} 中。这包括多个三元组以有条件地确定要渲染的内容。您可以根据您的风格需求,将加载和错误场景替换为您可以在其他地方定义的更充实的组件。