카테고리 없음

리액트 setState 비동기에 주의하라

jrpark91 2019. 6. 27. 18:25

setState는 비동기이다.

비동기이기 때문에 일어날 수 있는 실수를 정리했다.

예로들 예제는 클릭할때 마다 1씩 증가하는 스코어 키퍼다.

먼저 이와같이 스테이트가 정의 되어있다.

this.state = {score: 0}

 

1) 잘못된 setState 사용

singleUp() {
    this.setState({score: this.state.score + 1})
}

tripleUp() { // 이 함수가 문제가 된다.
    this.setState({score: this.state.score + 1})
    this.setState({score: this.state.score + 1})
    this.setState({score: this.state.score + 1})
}

singleUp은 잘 동작하지만 tripleUp은 3이 증가하는 것이 아니라 1만 증가한다.

그 이유는 현재 setState가 실행될 때 이전 setState가 끝나있다는 보장이 없기 때문이다.

즉 마지막 setSatate만 적용되는 것이다.

 

2) 올바른 사용

tripleUp() {
    this.setState(function(st) {
        return {score: st.score + 1}
    })
    this.setState(function(st) {
        return {score: st.score + 1}
    })
    this.setState(function(st) {
        return {score: st.score + 1}
    })
}

다음과 같이 callBack으로 실행순서를 정리해주면 정리가 된다.

callback은 새로운 state를 리턴해줘야 한다.

 

3) 올바른 사용 업그레이드 버전

incrementScore(curState) {
    return {score: st.score + 1}
})

tripleUp() {
    this.setState(incrementScore);
    this.setState(incrementScore);
    this.setState(incrementScore);
}