React TypeScript类组件中如何展示接口返回的对象元素?
解决React TypeScript类组件中展示接口返回对象的问题
核心问题分析
- render内发起请求导致重复调用:
render会在组件多次重渲染时执行,把接口请求写在这里会触发重复请求,所以控制台打印两次结果。 - 变量未初始化:
case_value仅声明未赋值,默认是undefined,调用push自然报错。 - 数据类型不匹配:接口返回的是单个对象,不是数组,没必要用数组存储,直接存对象即可。
- 未用组件状态管理:类组件需通过
state存储接口数据,这样数据更新时组件会自动重渲染展示内容。
修正步骤与完整代码
1. 定义状态类型与组件状态
先给接口返回的数据定义TS类型,再初始化组件状态:
// 对应接口返回的对象结构定义类型 interface CaseDetailData { id: string; creation_date: string; case_type: string; current_stage: string; last_change_date: string; status: number; } class CaseDetail extends React.Component<CaseDetailProps> { // 初始化组件状态,包含加载状态、数据、错误信息 state = { isLoading: true, caseDetail: null as CaseDetailData | null, error: null as string | null };
2. 在生命周期钩子中发起请求
用componentDidMount钩子,组件挂载时仅发起一次请求:
async componentDidMount() { try { const url = caseDetailUrl + this.props.id; // 等待Promise返回结果 const res = await Dependencies.backend.getList(url); // 确认res是预期的对象类型(如果后端返回数组,就取第一个元素:(res as CaseDetailData[])[0]) const caseData = res as CaseDetailData; // 更新状态,触发组件重渲染 this.setState({ caseDetail: caseData, isLoading: false }); } catch (err) { this.setState({ error: '加载数据失败', isLoading: false }); } }
3. 在render中展示数据
根据状态渲染加载、错误或正常内容:
render() { const { isLoading, caseDetail, error } = this.state; if (isLoading) { return <div>加载中...</div>; } if (error) { return <div>{error}</div>; } // 确保caseDetail存在后再渲染字段 return ( <div className="caseDetail"> <h1>案件详情</h1> <h3>ID: {caseDetail.id}</h3> <p>创建日期: {caseDetail.creation_date}</p> <p>案件类型: {caseDetail.case_type}</p> <p>最后修改日期: {caseDetail.last_change_date}</p> <p>状态: {caseDetail.status === 1 ? '有效' : '无效'}</p> </div> ); }
完整组件代码
import React from "react"; import { Dependencies } from "../../../shared/utils/dependencies"; import { caseDetailUrl } from "../../constants/backend-constants"; interface CaseDetailProps { id: string; } // 接口返回数据的类型定义 interface CaseDetailData { id: string; creation_date: string; case_type: string; current_stage: string; last_change_date: string; status: number; } class CaseDetail extends React.Component<CaseDetailProps> { state = { isLoading: true, caseDetail: null as CaseDetailData | null, error: null as string | null }; async componentDidMount() { try { const res = await Dependencies.backend.getList(caseDetailUrl + this.props.id); // 如果后端返回数组,就取第一个元素:const caseData = (res as CaseDetailData[])[0]; const caseData = res as CaseDetailData; this.setState({ caseDetail: caseData, isLoading: false }); } catch (err) { this.setState({ error: '加载案件详情失败', isLoading: false }); } } render() { const { isLoading, caseDetail, error } = this.state; if (isLoading) { return <div>加载中...</div>; } if (error) { return <div className="error">{error}</div>; } return ( <div className="caseDetail"> <h1>案件详情</h1> <div className="detail-item"> <span>ID:</span> <span>{caseDetail.id}</span> </div> <div className="detail-item"> <span>创建日期:</span> <span>{caseDetail.creation_date}</span> </div> <div className="detail-item"> <span>案件类型:</span> <span>{caseDetail.case_type}</span> </div> <div className="detail-item"> <span>当前阶段:</span> <span>{caseDetail.current_stage || '无'}</span> </div> <div className="detail-item"> <span>最后修改日期:</span> <span>{caseDetail.last_change_date}</span> </div> <div className="detail-item"> <span>状态:</span> <span>{caseDetail.status === 1 ? '有效' : '无效'}</span> </div> </div> ); } } export default CaseDetail;
额外说明
- 如果
getList实际返回数组(比如通用列表接口),就把请求后的赋值改成const caseData = (res as CaseDetailData[])[0]; - 加入加载和错误状态是为了避免空值报错,提升用户体验
- 类组件必须用
setState更新状态,直接修改变量不会触发重渲染
内容的提问来源于stack exchange,提问作者edche
相关产品推荐
相关产品推荐

