在React项目中添加Redux

时间:2019-04-21 21:24:07

标签: javascript reactjs react-native redux

在React项目中添加redux(使用Redux重构一个简单项目)

考虑一个简单的项目,一个使用两个按钮的计数器应用程序,一个用于递增,另一个用于递减计数器值。

在实际情况下,我们使用状态来保持计数器值,如下所示:

App.js 中:

import React, {Component} from 'react';
import CounterApp from './CounterApp'

class App extends Component {
  render() {
    return (
      <CounterApp/>
    );
  }
}

export default App;

CounterApp.js 中:

import React, {Component} from 'react';

class CounterApp extends Component {
  state = {
    counter: 0
  };

  handleIncrement = () => {
    this.setState(prevState => ({
      counter: prevState.counter + 1
    }))
  };

  handleDecrement = () => {
    this.setState(prevState => ({
      counter: prevState.counter - 1
    }))
  };

  render() {
    return (
      <div>
        <button onClick={this.handleIncrement}>Increment</button>
        <p>{this.state.counter}</p>
        <button onClick={this.handleDecrement}>Decrement</button>
      </div>
    );
  }
}

export default CounterApp;

一个简单而基本的示例,该示例使用react类组件实现并由两个函数处理程序(handleIncrementhandleDecrement)处理

还有一个state,其值为counter

  

我正在使用prevState,因为这是当您在this.state.中强制使用setState时的最佳实践!

现在, Redux 的实现将是什么?

1 个答案:

答案 0 :(得分:7)

首先,您需要通过npmyarn redux react-redux 软件包安装到项目中。

您只需使用一行代码即可安装它们:

npm install redux react-redux --save

或带有纱线:

yarn add redux react-redux

现在返回项目并使用以下名称创建3个文件:

action.jsreducer.jsstore.js

打开action.js文件。我们应该为此应用程序执行两个操作。一种是增量,另一种是递减。

action.js

const INCREMENT_COUNTER = 'INCREMENT_COUNTER';
const DECREMENT_COUNTER = 'DECREMENT_COUNTER';

const increment = () => ({type: INCREMENT_COUNTER});
const decrement = () => ({type: DECREMENT_COUNTER});

export {
  INCREMENT_COUNTER,
  DECREMENT_COUNTER,
  increment,
  decrement
}
  

action是从组件分派到redux的简单函数   通过减速器更改store(状态)。

所以我们应该更改 reducer.js

import {INCREMENT_COUNTER, DECREMENT_COUNTER} from "./action";

const initialState = {
  counter: 0
};

const reducer = (state = initialState, action) => {
  switch (action.type) {
    case(INCREMENT_COUNTER):
      return {
        ...state,
        counter: state.counter + 1
      };
    case (DECREMENT_COUNTER):
      return {
        ...state,
        counter: state.counter - 1
      };
    default:
      return state
  }
};

export default reducer

使用redux的3条主要原则:

  

1-真理的单一来源。您整个应用程序的状态是   存储在单个商店内的对象树中。

     

2-状态为只读。更改状态的唯一方法是发出   一个动作,一个描述发生了什么的对象。

     

3-使用纯函数进行更改。

根据第二个原则,我们必须假定状态是不可变的,并且每种情况(在开关中)必须单独返回状态。 在返回状态中使用... state表示如果initialState将来会更改,则这些情况将正常工作(在此示例中,这是没有必要的。)

我们的动作函数是纯函数(第三原理)

以及最后一个新文件 store.js

import {createStore} from "redux";
import reducer from './reducer'

const store = createStore(reducer);

export default store;

现在我们应该将此商店应用于我们的App组件。 因此,打开App.js文件并进行以下更改:

App.js 中:

import React, {Component} from 'react';
import CounterApp from './CounterApp'
import {Provider} from 'react-redux'
import store from './store'

class App extends Component {
  render() {
    return (
      <Provider store={store}>
        <CounterApp/>
      </Provider>
    );
  }
}

export default App;

提供者包装了CounterApp组件,并将store传播到AppCounterApp以及所有其他子组件。

最后,更改 CounterApp.js

import React, {Component} from 'react';
import {connect} from "react-redux";
import {increment, decrement} from "./action";

class CounterApp extends Component {

  handleIncrement = () => this.props.dispatch(increment());

  handleDecrement = () => this.props.dispatch(decrement());

  render() {
    return (
      <div>
        <button onClick={this.handleIncrement}>Increment</button>
        <p>{this.props.counter}</p>
        <button onClick={this.handleDecrement}>Decrement</button>
      </div>
    );
  }
}

const mapStateToProps = state => {
  const counter = state.counter;
  return {counter}
};

export default connect(mapStateToProps)(CounterApp);

我们正在使用incrementdecrement操作将操作分派到redux。

state被删除,我们创建了一个特殊的函数mapStateToProps' and use connect`来将状态连接到组件道具。

完成了!