【问题标题】:Map properties to state in react-redux将属性映射到 react-redux 中的状态
【发布时间】:2017-03-31 17:06:18
【问题描述】:

我有一个使用state 向用户提供数据的组件。例如<div>this.state.variableInState</div>。该组件可以调度某些方法(例如在onClick 操作上)。我目前正在使用react-reduxconnect 方法将store 映射到props。有没有办法可以在发送后setState

// actions
export function executeAction() {
  return function (dispatch, getState) {
    dispatch({
      type: 'MY_ACTION',
      payload: axios.get('/some/url')
    });
  };
}
// reducer

export default function (state = {}, action) {
  switch (action.type) {
    case 'MY_ACTION_FULFILLED':
      return {...state, myVariable: action.payload.data}
  }
}
//component
class MyComponent extends Component {
  render() {
    (<div onClick={this.props.executeAction.bind(this)}>
      {this.state.variableInState}
      </div>)
  }

  someOtherMethod() {
    // I want to operate with state here, not with props
    // that's why my div gets state from this.state instead of this.props
    this.setState({variableInState: 'someValue'})
  }
}


export default connect((state, ownProperties) => {
  return {
    // So I want to change MyComponent.state.variableInState here
    // but this method updates MyComponent props only
    // What can I do?
    variableInProps: state.myVariable
  }
}, {executeAction})(MyComponent);

【问题讨论】:

    标签: javascript reactjs redux react-redux


    【解决方案1】:

    无论我理解什么,您要做的就是将组件的道具转换为组件自己的状态。您可以随时在组件中的 componentWillReceiveProps 生命周期方法中将组件的 props 更改为组件的状态,如下所示。

    //component
    class MyComponent extends Component {
      componentWillReceiveProps(newProps){
         if(newProps.variableInProps != this.props.variableInProps){
             this.setState({variableInState: newProps.variableInProps })
         }
      }
      render() {
        (<div onClick={this.props.executeAction.bind(this)}>
          {this.state.variableInState}
          </div>)
      }
    
      someOtherMethod() {
        // I want to operate with state here, not with props
        // that's why my div gets state from this.state instead of this.props
        this.setState({variableInState: 'someValue'})
      }
    }
    
    
    export default connect((state, ownProperties) => {
      return {
        // So I want to change MyComponent.state.variableInState here
        // but this method updates MyComponent props only
        // What can I do?
        variableInProps: state.myVariable
      }
    }, {executeAction})(MyComponent);
    

    componentWillReceiveProps 方法总是由 react 每当有新的 props 进入组件时执行,所以这是根据你的 props 更新组件状态的正确位置。

    更新:

    componentWillReceiveProps 已被弃用。因此,您可以使用componentDidUpdate 方法代替此方法来执行此操作。 componentDidUpdate 方法将先前的道具和先前的状态作为参数。所以你可以检查 props 的变化,然后设置 state。

    componentDidUpdate(prevProps) {
      if(prevProps.variableInProps !== this.props.variableInProps){
        this.setState({variableInState: this.props.variableInProps })
      }
    }
    

    【讨论】:

    • componentWillReceiveProps 已被弃用,您可以改用componentDidUpdate
    【解决方案2】:

    我认为您不应该像这样直接更改状态。为什么不调用另一个动作来执行你想要的?

    在使用 Redux 时,状态应该是不可变的。你应该派发一个动作。 Reducer 应该接收操作和当前状态,并返回一个新的状态对象,其中包含您想要进行的更改。 检查这个:http://redux.js.org/docs/introduction/ThreePrinciples.html#changes-are-made-with-pure-functions

    【讨论】:

    • 但是如何通过 dispatch 改变状态呢?我的 reducer 已经返回了新的状态,但是这个状态映射到 props,而不是 state。我如何将它也映射到状态?
    【解决方案3】:

    当然可以,onClick 绑定到一些函数,如下所示:

    onClick={this.myfunction.bind(this)}
    

    然后将这个myfuntion定义为:

    myfunction() {
        this.setState({ somestate: value });
        this.props.executeAction();
    }
    

    这里 setState 会改变原生组件的状态,如果 reducer 这么定义,调用 action 会改变 redux 的状态。这些状态是独立的。

    连接包装器(第一个参数)将状态映射到道具(redux 状态以反应道具)而不是组件状态本身。

    很好的问题是为什么你需要两者,当然有一些例子可能有用......

    一般来说,如果您需要全局所需的状态,则使用 redux 状态(很容易应用于所有组件),对于某些本地状态,请使用 react 原生状态。 (例如当你构建一些像自定义复选框这样的 ui 组件时)

    【讨论】:

    • 状态取决于休息响应。这是通过调度执行的
    • 准确来说,redux reducer 不会改变原生组件(react 状态),也不应该,我写的是当你想调度一些动作但也改变原生反应状态的情况。
    【解决方案4】:

    还有静态getDerivedStateFromProps

    static getDerivedStateFromProp(nextProps, prevState) {
      return {stateVar: nextProps.var} // this will propagate as component state
    }
    

    【讨论】:

      猜你喜欢
      • 2017-11-07
      • 1970-01-01
      • 2021-02-13
      • 1970-01-01
      • 1970-01-01
      • 2018-09-13
      • 1970-01-01
      • 2021-09-12
      • 2016-12-03
      相关资源
      最近更新 更多