react案例—實現最簡登錄

react案例—實現最簡登錄

文中代碼都是片段,主要說明主要邏輯,完整代碼參考 github
用到的庫是 react-router + react-redux

通過 react-route 的快速入門我們很容易可以得到這樣的路由

最終效果

login.gif

主要邏輯

我們進一步來改造,實現進來默認到登錄頁,登錄成功看到菜單及對應組件。
簡單分析下需求:

  • 用戶打開頁面‘/’時,會先判斷是否登錄,我們用一個狀態 isLogin 來判斷
  • 登錄成功之後,isLogin 會改變爲 true,並且 isLogin 和用戶信息會在路由組件中傳遞。

這裏使用 react-redux 來實現這樣一個狀態傳遞。
react-redux 提供了 connect 函數來將 state 映射到props上並傳遞給組件,使用之前需用 Provide 組件將原本的App包起來,將 store 作爲 props 傳遞。

src/store/index.js

創建store

import {createStore, combineReducers} from 'redux';
import {userReducer} from "./userReducer";

const store = createStore(combineReducers({user: userReducer}))

export default store;

src/store/userReducer.js

這裏的操作很簡單,只需要用戶登錄成功後,通過store.dispatch 將 isLogin 狀態更改爲 true

// 定義修改規則 登錄
const initalUserInfo = {
  isLogin: false, //判斷是否登錄
};
export function userReducer(
  state = {...initalUserInfo}, action) {
  switch (action.type) {
    case "LOGIN_SUCCESS":
      return {
        isLogin: true
      };
   
    default:
      return state;
  }
}

src/index.js

image.png

這樣 store 就註冊好了,接下來改造文章開頭的路由

src/App.js

// 我們把之前的路由菜單改一下,非登錄狀態進入 /login,登錄狀態顯示菜單
function App(){
  return (
    <BrowserRouter>
        <Route path='/login' component={LoginPage} />
        <PrivateRoute path='/'>
          <ul>
            <li><Link to='/'>主頁</Link></li>
            <li><Link to='/message'>消息</Link></li>
            <li><Link to='/search'>發現</Link></li>
            <li><Link to='/my'>我的</Link></li>
          </ul>
          <Switch>
            <Route exact path='/' component={HomePage} />
            <Route path='/message' component={MessagePage}/>
            <Route path='/search' component={SearchPage}/>
            <Route path='/my' component={MyPage}/>
          </Switch>
        </PrivateRoute>
    </BrowserRouter>
  )
}

src/route/privateRoute.js

privateRoute 在這裏起到路由守衛的作用,即進入頁面之前先判斷登錄狀態

import React from 'react';
import {Redirect, Route} from 'react-router-dom';
import {connect} from 'react-redux'

export default connect(
  ({user}) => ({
    isLogin: user.isLogin
  })
)(
  function PrivateRoute({children, isLogin, ...rest}) {
    return (
      <Route
        {...rest}
        render={({location}) =>
          isLogin ? (
            children
          ) : (<Redirect
              to={{
                pathname: "/login", state:
                  {redirect: location.pathname}
              }}
            />
          )
        }
      />
    );
  });

src/pages/loginPage.js

登錄頁面的邏輯主要在登錄成功之後的處理

// 表單提交
submit = ()=>{
  const {username, password} = this.state;
  // 這裏保留一個成功的用戶名和密碼
  if (username === 'admin' && password === 'admin'){
    store.dispatch({type: 'LOGIN_SUCCESS'})
    this.props.history.push('/')
  } else {
    store.dispatch({type: 'LOGIN_FAILURE'})
  }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章