天天看點

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建

一.基礎配置

1. 路由配置

(1). 建立項目,已經引入了Vue-Router,這裡的版本為:3.2.0,并自動建立了router→index.js檔案。

(2). 在index.js檔案中:

 A. 導入vue、vue-router

 B. 導入其它子頁面

 C. 配置路由規則,預設進入/login登入頁面,home頁面下配置子路由,home頁面需要添加路由占位符

<router-view></router-view>      

 D. 挂載路由導航守衛,token不存在的話,不允許單獨跳轉到除了login以外的頁面,同意跳轉到登入頁面。

 E. 預設對外導出

代碼分享:

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
import Vue from 'vue'
import VueRouter from 'vue-router'
// 導入各個子頁面(可以用相對路徑 或 根路徑,@代表根路徑)
import Login from '../components/Login.vue'
import Home from '@/components/Home.vue'
import Welcome from '@/components/Welcome.vue'
import Users from '@/components/user/Users.vue'
import Rights from '@/components/power/Rights.vue'
import Roles from '@/components/power/Roles.vue'
import Params from '@/components/goods/Params.vue'
import GoodsList from '@/components/goods/List.vue'
import Add from '@/components/goods/Add.vue'
import Order from '@/components/order/Order.vue'
import Report from '@/components/report/Report.vue'

Vue.use(VueRouter)

const router = new VueRouter({
  routes: [{
      path: '/',
      redirect: '/login'
    },
    {
      path: '/login',
      component: Login
    },
    {
      path: '/home',
      component: Home,
      redirect: '/welcome',
      children: [{
          path: '/welcome',
          component: Welcome
        },
        {
          path: '/users',
          component: Users
        },
        {
          path: '/rights',
          component: Rights
        },
        {
          path: '/roles',
          component: Roles
        },
        {
          path: '/params',
          component: Params
        },
        {
          path: '/goods',
          component: GoodsList
        },
        {
          path: '/goods/add',
          component: Add
        },
        {
          path: '/orders',
          component: Order
        },
        {
          path: '/reports',
          component: Report
        }
      ]
    }
  ]
})


// 挂載路由導航守衛
router.beforeEach((to, from, next) => {
  // to 将要通路的路徑
  // from 代表從哪個路徑跳轉而來
  // next 是一個函數,表示放行
  // next()  放行    next('/login')  強制跳轉
  if (to.path === '/login') return next()
  // 擷取token
  const tokenStr = window.sessionStorage.getItem('token')
  if (!tokenStr) return next('/login')
  next()
})


// 預設導出
export default router      

View Code

PS. 如何手動調用跳轉:

this.$router.push('/home')      

2. 樣式配置

(1). 項目中要用到less文法,是以需要安裝less 和 less-loader,開發依賴

【npm install less -D】      (4.1.1)

【npm install [email protected] -D】   (7.3.0)不能裝太高版本      

(2) style标簽中增加 lang="less",表示支援less文法,另外增加scoped屬性,代表寫的樣式僅目前頁面有效。

<style lang="less" scoped></style>      

3. 靜态資源

 靜态資源,比如全局樣式、第三方字型檔案等,統一放在 src下的assets檔案夾中。然後在main.js檔案中導入全局樣式和第三方字型。

// 導入字型圖示
import './assets/fonts/iconfont.css'
// 導入全局樣式表
import './assets/css/global.css'       

4. axios封裝和使用

(1). 通過指令【npm install axios -save】進行安裝

(2). 在main.js中進行導入

(3). 配置baseURL、請求攔截中添加表頭(存放token)、利用Vue.prototype進行全局對象封裝為$http。

// 導入axios并進行配置
import axios from 'axios'
axios.defaults.baseURL = 'http://127.0.0.1:8888/api/private/v1/'
axios.interceptors.request.use(config => {
  // 添加表頭資訊
  config.headers.Authorization = window.sessionStorage.getItem('token');
  return config;
})
Vue.prototype.$http = axios      

(4).使用:以post請求為例,借助async和await,幹掉回調,以同步的編碼方式進行擷取,然後利用解構指派,拿到傳回對象中的data屬性(注意,不是接口傳回值的data),然後起别名為res。

async login () {
   const {
     data: res
   } = await this.$http.post('login', this.loginForm)
   if (res.meta.status !== 200) return this.$message.error('登入失敗!')
   this.$message.success('登入成功')
}      

5. ESLint警告處理

建立項目的時候,選擇安裝了ESLint,相關程式集如下:

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建

(1). 運作指令【npm run lint】或者(npm run serve), 會報很多錯誤和警告,如下圖:

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建

但有些警告我們并不像處理,也不想讓它提示,那麼就在根目錄下的 .eslintrc.js 檔案中進行關閉 

rules: {
    'no-console': process.env.NODE_ENV === 'production' ? 'warn' : 'off',
    'no-debugger': process.env.NODE_ENV === 'production' ? 'warn' : 'off',
    // 禁止超過1個空行報錯規則,0代表關掉
    'no-multiple-empty-lines': 0,
    'no-tabs': 0,
    'eslint-disable-next-line': 0,
    'space-before-function-paren':0,
    'indent':0

  }      

(2). 如果你想更加簡單粗暴的關掉驗證,可以新增一個.eslintignore檔案,直接關掉 .vue檔案和 .js檔案的驗證。

*.vue
*.js      

二. 基礎元件

1. Form表單

(1). 擷取表單對象

 在el-form中新加一個ref=“loginFormRef”屬性,然後通過 this.$refs.loginFormRef 就可以擷取該對象了,可以調用該對象的相關方法。 

PS:這是一種通用的方式,适用于任何element元件。 

(2). 值綁定 

 在el-form中通過 :model="loginForm"進行整個對象的綁定,然後在對應 input标簽中通過 v-model="loginForm.username"進行子屬性的綁定。 

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建

(3).驗證規則綁定(含自定義驗證)

  在el-form中通過 :rules="loginFormRules"進行整個驗證規則對象的綁定,然後在對應el-form-item标簽中通過 prop="屬性值" 進行子屬性規則的綁定。 

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建

PS 自定義驗證規則:

 需要自定義一個方法,方法有3個參數,rule、value、callback,重點是後兩個;value是驗證的内容,callback是回調,驗證通過,直接傳回 callback(); 驗證不通過,則聲明 callback(new Error('請輸入數字值'));

然後定義的方法賦給validator屬性。

代碼如下:

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
<el-form :model="ruleForm" status-icon :rules="rules" ref="ruleForm" label-width="100px" class="demo-ruleForm">
  <el-form-item label="密碼" prop="pass">
    <el-input type="password" v-model="ruleForm.pass" autocomplete="off"></el-input>
  </el-form-item>
  <el-form-item label="确認密碼" prop="checkPass">
    <el-input type="password" v-model="ruleForm.checkPass" autocomplete="off"></el-input>
  </el-form-item>
  <el-form-item label="年齡" prop="age">
    <el-input v-model.number="ruleForm.age"></el-input>
  </el-form-item>
  <el-form-item>
    <el-button type="primary" @click="submitForm('ruleForm')">送出</el-button>
    <el-button @click="resetForm('ruleForm')">重置</el-button>
  </el-form-item>
</el-form>
<script>
  export default {
    data() {
      var checkAge = (rule, value, callback) => {
        if (!value) {
          return callback(new Error('年齡不能為空'));
        }
        setTimeout(() => {
          if (!Number.isInteger(value)) {
            callback(new Error('請輸入數字值'));
          } else {
            if (value < 18) {
              callback(new Error('必須年滿18歲'));
            } else {
              callback();
            }
          }
        }, 1000);
      };
      var validatePass = (rule, value, callback) => {
        if (value === '') {
          callback(new Error('請輸入密碼'));
        } else {
          if (this.ruleForm.checkPass !== '') {
            this.$refs.ruleForm.validateField('checkPass');
          }
          callback();
        }
      };
      var validatePass2 = (rule, value, callback) => {
        if (value === '') {
          callback(new Error('請再次輸入密碼'));
        } else if (value !== this.ruleForm.pass) {
          callback(new Error('兩次輸入密碼不一緻!'));
        } else {
          callback();
        }
      };
      return {
        ruleForm: {
          pass: '',
          checkPass: '',
          age: ''
        },
        rules: {
          pass: [
            { validator: validatePass, trigger: 'blur' }
          ],
          checkPass: [
            { validator: validatePass2, trigger: 'blur' }
          ],
          age: [
            { validator: checkAge, trigger: 'blur' }
          ]
        }
      };
    },
    methods: {
      submitForm(formName) {
        this.$refs[formName].validate((valid) => {
          if (valid) {
            alert('submit!');
          } else {
            console.log('error submit!!');
            return false;
          }
        });
      },
      resetForm(formName) {
        this.$refs[formName].resetFields();
      }
    }
  }
</script>      

View Code 

(4). 表單校驗

 調用validate進行表單内所有内容的校驗

this.$refs.loginFormRef.validate(valid => {
        console.log(valid)
        if (!valid) return
        // 下面表示校驗通過,進行業務編寫
  
 })      

(5). 表單重置 

this.$refs.loginFormRef.resetFields()      

2. Message消息提示 

(1). 全局引入和封裝

import { Message } from 'element-ui'
Vue.prototype.$message = Message      

(2). 使用 

this.$message.success('登入成功')
this.$message.error('登入失敗!')      

this.$message({
          showClose: true,
          message: '錯了哦,這是一條錯誤消息',
          type: 'error'
});      

三. 登入界面

1. 效果分享

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建

2. 代碼分享

第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
第二節:基礎配置(路由、less、靜态資源、axios、ESLint)、基礎元件(Form、Message) 之登入頁面搭建
<template>
  <div class="login_container">
    <div class="login_box">
      <!-- 頭像區域 -->
      <div class="avatar_box">
        <img src="../assets/logo.png" alt="">
      </div>
      <!-- 登入表單區域 -->
      <el-form ref="loginFormRef" :model="loginForm" :rules="loginFormRules" label-width="0px" class="login_form">
        <!-- 使用者名 -->
        <el-form-item prop="username">
          <el-input v-model="loginForm.username" prefix-icon="iconfont icon-user"></el-input>
        </el-form-item>
        <!-- 密碼 -->
        <el-form-item prop="password">
          <el-input v-model="loginForm.password" prefix-icon="iconfont icon-3702mima" type="password">
          </el-input>
        </el-form-item>
        <!-- 按鈕區域 -->
        <el-form-item class="btns">
          <el-button type="primary" @click="login">登入</el-button>
          <el-button type="info" @click="resetLoginForm">重置</el-button>
        </el-form-item>
      </el-form>
    </div>
  </div>
</template>

<script>
export default {
  data () {
    return {
      // 這是登入表單的資料綁定對象
      loginForm: {
        username: 'admin',
        password: '123456'
      },
      // 這是表單的驗證規則對象
      loginFormRules: {
        // 驗證使用者名是否合法
        username: [{
          required: true,
          message: '請輸入登入名稱',
          trigger: 'blur'
        },
        {
          min: 3,
          max: 10,
          message: '長度在 3 到 10 個字元',
          trigger: 'blur'
        }
        ],
        // 驗證密碼是否合法
        password: [{
          required: true,
          message: '請輸入登入密碼',
          trigger: 'blur'
        },
        {
          min: 6,
          max: 15,
          message: '長度在 6 到 15 個字元',
          trigger: 'blur'
        }
        ]
      }
    }
  },
  methods: {
    // 1.重置事件
    resetLoginForm () {
      // 通過$refs可以達到表單中ref的屬性值
      this.$refs.loginFormRef.resetFields()
    },
    // 2. 登入事件
    login () {
      // 2.1 先對整個form表單進行規則校驗
      this.$refs.loginFormRef.validate(async valid => {
        console.log(valid)
        if (!valid) return
        // 2.2 校驗通過,發送請求
        const {
          data: res
        } = await this.$http.post('login', this.loginForm)
        if (res.meta.status !== 200) return this.$message.error('登入失敗!')
        this.$message.success('登入成功')
        // 2.3. 将登入成功之後的 token,儲存到用戶端的 sessionStorage 中
        // 2.3.1 項目中出了登入之外的其他API接口,必須在登入之後才能通路
        // 2.3.2 token 隻應在目前網站打開期間生效,是以将 token 儲存在 sessionStorage 中
        window.sessionStorage.setItem('token', res.data.token)
        // 2.4  通過程式設計式導航跳轉到背景首頁,路由位址是 /home
        this.$router.push('/home')
      })
    }
  }
}
</script>

<style lang="less" scoped>
  .login_container {
    background-color: #2b4b6b;
    height: 100%;
  }

  .login_box {
    width: 450px;
    height: 300px;
    background-color: #fff;
    border-radius: 3px;
    position: absolute;
    left: 50%;
    top: 50%;
    transform: translate(-50%, -50%);

    .avatar_box {
      height: 130px;
      width: 130px;
      border: 1px solid #eee;
      border-radius: 50%;
      padding: 10px;
      box-shadow: 0 0 10px #ddd;
      position: absolute;
      left: 50%;
      transform: translate(-50%, -50%);
      background-color: #fff;

      img {
        width: 100%;
        height: 100%;
        border-radius: 50%;
        background-color: #eee;
      }
    }
  }

  .login_form {
    position: absolute;
    bottom: 0;
    width: 100%;
    padding: 0 20px;
    box-sizing: border-box;
  }

  .btns {
    display: flex;
    justify-content: flex-end;
  }
</style>      

!

  • 作       者 : Yaopengfei(姚鵬飛)
  • 部落格位址 : http://www.cnblogs.com/yaopengfei/
  • 聲     明1 : 如有錯誤,歡迎讨論,請勿謾罵^_^。
  • 聲     明2 : 原創部落格請在轉載時保留原文連結或在文章開頭加上本人部落格位址,否則保留追究法律責任的權利。