簡體   English   中英

在componentDidMount內部的回調中設置狀態

[英]Setting State in a Callback inside of componentDidMount

我目前正在使用React 16.3(React Native),寫在這里 ,它表明我應該在componentDidMount而不是componentWillMount內發出任何異步請求,因為這將很快被棄用。

不幸的是,我在嘗試獲取componentDidMount內部的數據時收到無操作警告,並將從axios請求返回的數據設置為我的狀態。

這是一個片段

export default class MyComponent extends Component {
    state = {
      myData: []
    }

    componentDidMount() {
      axios.get('api-endpoint')
      .then(res => this.setState({ myData: res.data })
    }
    render() { return <View>...</View> }
}

和警告-

Warning: Can only update a mounted or mounting component. 
This usually means you called setState, replaceState, or 
forceUpdate on an unmounted component. This is a no-op.

Please check the code for the MyComponent component.

這就是在組件中包含異步代碼的問題。 例如,當Promise解析(可能需要幾秒鍾)時,用戶可能已經導航到應用程序的另一部分,因此,當Promise解析並嘗試執行setState ,會收到錯誤消息,您嘗試更新未安裝的組件。

我的建議是為異步邏輯使用類似redux-thunk,redux-saga或redux-observable之類的東西。但是,您可以進行簡單的檢查- 但這是一種反模式

export default class MyComponent extends Component {
    state = {
      myData: []
    }

    componentDidMount() {
      this.isMounted = true;

      axios.get('api-endpoint')
      .then(res => {
        if(this.isMounted) {
          this.setState({ myData: res.data })
        }
      })
    }

    componentWillUnmount() {
      this.isMounted = false;
    }
    render() { return <div>...</div> }
}

我的建議是遵循適當的助焊劑。 您可以在componentDidMount()MyComponent附加商店偵聽器,如下所示。

componentDidMount() {
   //call async data fecthing method here
   store.addListener('eventname', onDataReceipt);
}

在此之前,您可以將狀態更改邏輯移動到onDataReceipt方法。 componentDidMount()調用異步數據提取,並dispatch商店已注冊到的操作。 然后從商店發出事件。 由於您已經在componentDidMount()訂閱了該事件,因此將在事件發射時執行onDataReceipt() 也不要忘記刪除componentWillUnMout()中的偵聽器

componentWillUnMount() {
   store.removeListener('eventname', onDataReceipt);
}

助焊劑將負責其余的工作,您無需擔心警告。

更新—之所以要卸載父組件,是因為我要在其父組件中設置狀態,所以要卸載該組件。 當在父組件中設置狀態時,它強制重新渲染該組件,這使樹陷入困境並在我的異步請求中間被卸下。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM