在src目錄下創建四個js文件分別為 index.js, action.js, reducers.js, state.js
分別用來創建store倉庫,異步請求,真正用到的數據集合,默認數據設置
需要用到的工具有
Npm install redux -s
狀態管理工具,與React沒有任何關系,其他UI框架也可以使用Redux
Npm install react-redux -s
React插件,作用:方便在React項目中使用Redux
Npm install react-thunk -s
中間件,作用:支持異步action
目錄:
image.png
reducers.js:
// 它就是將來真正要用到的數據,我們將其統一放置在reducers.js文件 import {combineReducers} from 'redux' import defaultState from './state.js' function pageTitle (state = defaultState.pageTitle,action) { // 不同的action有不同的處理邏輯 switch (action.type) { case 'SET_PAGE_TITLE': return action.data default: return state } } function user (state = defaultState.user, action){ switch (action.type) { case 'SET_USER': return action.data default: return state } } export default combineReducers({ pageTitle, user })
action.js:
// 現在我們已經創建了reducer,但是還沒有對應的action來操作它們,所以接下來就來編寫action import axios from 'axios' import qs from 'qs' import { Modal} from 'antd-mobile'; import 'antd-mobile/dist/antd-mobile.css'; const alert = Modal.alert; // 常量修改 export function setPageTitle (data) { return (dispatch) => { dispatch({ type: 'SET_PAGE_TITLE', data: data }) } } // 異步修改 // 用戶登錄,將用戶信息存儲在倉庫 export function setUser (userName,password){ return (dispatch) => { axios.post('http://xx.xx.xx.xx:8888/user-server/login/userLogin',qs.stringify({ userName:userName, password:password })).then(res => { if(res.data.apistatus === 200){ dispatch({ type: 'SET_USER', data:res.data.result }) }else { alert('提示',res.data.msg , [ { text: '知道了', onPress: () => '' }, ]) } }) } }
index.js:
// index.js // applyMiddleware: redux通過該函數來使用中間件 // createStore: 用於創建store實例 import { applyMiddleware, createStore } from 'redux' // 中間件,作用:如果不使用該中間件,當我們dispatch一個action時,需要給dispatch函數傳入action 對象;但如果我們使用了這個中間件,那么就可以傳入一個函數,這個函數接收兩個參數:dispatch和 getState。這個dispatch可以在將來的異步請求完成后使用,對於異步action很有用 import thunk from 'redux-thunk' // 引入reducer import reducers from './reducers.js' // 創建store實例 let store = createStore( reducers, applyMiddleware(thunk) ) export default store
state.js:
export default { pageTitle:"首頁", user:[] }
前面都是准備工作,實際使用如下:
讓store作用全部組件:
在app.js入口文件中:
import { Provider } from 'react-redux' import store from './store/index' render() { return ( <div> <Provider store = {store}> </Provider> </div> ) }
然后再組件中使用:
import React,{Component} from 'react'; import './login.css'; import '../public/alert.css' import {Link} from 'react-router-dom' import Input from '../public/input' import { connect } from 'react-redux' import { setUser } from '../../store/actions' import { Redirect } from 'react-router'; class Login extends Component { constructor(props){ super(props); this.state = { name:'手機號碼/郵箱號碼', password:'登錄密碼', name2:'', password2:'' } } getname(name){ this.setState({ name2:name }) } getpass(pass){ this.setState({ password2:pass }) } submit(){ let { setUser } = this.props let me = this; setUser(me.state.name2,me.state.password2); } render(){ let { user } = this.props if(user.acc_token){ return (<Redirect to="/"/>); }else { return ( <div id='login'> <p>{user.acc_token}</p> <h1>LOGO</h1> <div> <Input msg={this.state.name} gethandle={this.getname.bind(this)}/> <Input msg={this.state.password} gethandle={this.getpass.bind(this)}/> <button onClick={(e) => {this.submit(e)}}>登錄</button> </div> <p> <Link to='/Register'>注冊新賬號</Link> <span> | </span> <Link to=''>忘記登錄密碼</Link> </p> </div> ) } } 