React中new Promise包裹带回调的setState代码运行逻辑如何理解?
React setState 双参数与Promise封装运行逻辑
基础前提:setState的原生语法
React类组件的setState是异步更新API,原生支持两个入参:
- 第一个参数:待更新的state片段(支持对象形式或返回state对象的函数形式)
- 第二个参数:可选的回调函数,会在state更新落地、组件重新渲染完成后自动触发
疑问代码的运行流程
代码核心是把非Promise化的setState回调转换成Promise,适配async/await的异步流程控制,逐步骤运行逻辑如下:
// state初始化 constructor(props){ super(props); this.state = { articles:[], loading:true, page:1, totalResults : 0 } } // 点击下一页的处理逻辑 handleNextClick = async ()=>{ await new Promise(resolve => this.setState({page: this.state.page+1}, () => resolve())); await this.updateNews(); }
- 点击下一页触发
handleNextClick,首先创建新的Promise实例,Promise的执行器函数会立即同步执行 - 执行器内部调用
this.setState,提交page + 1的更新请求,此时因为setState异步,state不会立刻变更,Promise处于pending状态,await会阻塞后续代码执行 - React完成state更新、组件重新渲染结束后,自动触发setState的第二个参数(回调函数),执行
resolve(),Promise状态变为已完成 - await检测到Promise完成,恢复代码执行,调用
this.updateNews()请求新页码对应的新闻数据
封装目的说明
原生setState本身不返回Promise,直接对其使用await不会生效,无法保证后续的updateNews拿到更新后的page值。手动封装一层Promise的作用就是把setState的回调触发时机转换为Promise的完成时机,确保异步流程的时序正确。
注:代码中注释的
// same as await this.setState({page: this.state.page+1});是错误的,原生setState没有返回Promise的能力,直接await不会等待更新完成,会导致updateNews拿到旧的page值请求数据。
内容的提问来源于stack exchange,提问作者Himanshu Poddar
相关产品推荐
相关产品推荐

