Browse Source

单点登录

lirui 3 năm trước cách đây
mục cha
commit
c685c154fa
5 tập tin đã thay đổi với 210 bổ sung2 xóa
  1. 18 0
      src/api/login.js
  2. 3 1
      src/router/index.js
  3. 9 0
      src/router/routers.js
  4. 21 1
      src/store/modules/user.js
  5. 159 0
      src/views/middle.vue

+ 18 - 0
src/api/login.js

@@ -13,6 +13,24 @@ export function login(username, password, code, uuid) {
   })
 }
 
+export function sso(username, password) {
+  return request({
+    url: 'auth/sso',
+    method: 'post',
+    data: {
+      username,
+      password
+    }
+  })
+}
+
+export function ssoGetUser(token) {
+  return request({
+    url: '/api/thirdparty/v1/user/sso?token=' + token,
+    method: 'get'
+  })
+}
+
 export function getInfo() {
   return request({
     url: 'auth/info',

+ 3 - 1
src/router/index.js

@@ -9,7 +9,7 @@ import { filterAsyncRouter } from '@/store/modules/permission'
 
 NProgress.configure({ showSpinner: false })// NProgress Configuration
 
-const whiteList = ['/login']// no redirect whitelist
+const whiteList = ['/login', '/middle']// no redirect whitelist
 
 router.beforeEach((to, from, next) => {
   if (to.meta.title) {
@@ -44,6 +44,8 @@ router.beforeEach((to, from, next) => {
     /* has no token*/
     if (whiteList.indexOf(to.path) !== -1) { // 在免登录白名单,直接进入
       next()
+    } else if (to.path === '/middle') {
+      next()
     } else {
       next(`/login?redirect=${to.fullPath}`) // 否则全部重定向到登录页
       NProgress.done()

+ 9 - 0
src/router/routers.js

@@ -10,6 +10,15 @@ export const constantRouterMap = [
     component: (resolve) => require(['@/views/login'], resolve),
     hidden: true
   },
+  {
+    path: '/middle',
+    meta: {
+      title: '中间页',
+      noCache: true
+    },
+    component: (resolve) => require(['@/views/middle'], resolve),
+    hidden: true
+  },
   {
     path: '/404',
     component: (resolve) => require(['@/views/features/404'], resolve),

+ 21 - 1
src/store/modules/user.js

@@ -1,4 +1,4 @@
-import { login, getInfo, logout } from '@/api/login'
+import { login, getInfo, logout, sso } from '@/api/login'
 import { getToken, setToken, removeToken } from '@/utils/auth'
 
 const user = {
@@ -50,6 +50,26 @@ const user = {
       })
     },
 
+    // 单点登录
+    Sso({ commit }, userInfo) {
+      const rememberMe = false
+      return new Promise((resolve, reject) => {
+        sso(userInfo.username, userInfo.password).then(res => {
+          setToken(res.token, rememberMe)
+          commit('SET_TOKEN', res.token)
+          setUserInfo(res.user, commit)
+          // 第一次加载菜单时用到, 具体见 src 目录下的 permission.js
+          commit('SET_LOAD_MENUS', true)
+          // 存储用户密码用作单点登录子系统
+          localStorage.setItem('userPassword', userInfo.password)
+          commit('SET_USER_PASSWORD', userInfo.password)
+          resolve()
+        }).catch(error => {
+          reject(error)
+        })
+      })
+    },
+
     // 获取用户信息
     GetInfo({ commit }) {
       return new Promise((resolve, reject) => {

+ 159 - 0
src/views/middle.vue

@@ -0,0 +1,159 @@
+<template>
+  <el-row style="background-color: rgb(241, 242, 246);height: calc(100vh - 84px);">
+    <el-row>
+      <el-image :src="Background" />
+    </el-row>
+    <el-row class="routerCardPar">
+      <template v-for="(system, index) in systemList">
+        <el-card :key="system.id" class="routerCard" @click.native="sso(system.systemUrl)">
+          <img :src="system.storage.url">
+          <!--          <img src="@/assets/images/hyxt.png" />-->
+          <span>{{ system.systemName }}</span>
+        </el-card>
+      </template>
+    </el-row>
+  </el-row>
+</template>
+
+<script>
+import { ssoGetUser } from '@/api/login'
+import { mapGetters } from 'vuex'
+import crudDmSystem from '@/api/dm/system/dmSystem'
+import Background from '@/assets/images/bg.png'
+import { encrypt } from '@/utils/rsaEncrypt'
+
+export default {
+  name: 'Sso',
+  data() {
+    const token = this.$route.query.token
+    console.log(token)
+    return {
+      token: token,
+      systemList: [],
+      Background: Background
+    }
+  },
+  computed: {
+    ...mapGetters([
+      'user',
+      'userPassword'
+    ])
+  },
+  created() {
+    console.log(this.token)
+    this.getUser(this.token)
+  },
+  methods: {
+    getUser(token) {
+      ssoGetUser(token).then(res => {
+        const user = {
+          username: res.data.data.user.username,
+          password: res.data.data.user.ossPassword
+        }
+        this.$store.dispatch('Sso', user).then(() => {
+          crudDmSystem.queryByUserId(res.data.data.user.id).then(res => {
+            console.log('res', res)
+            this.systemList = res
+          })
+        })
+      })
+    },
+    sso(url) {
+      const username = encrypt(this.user.username)
+      const password = this.userPassword
+      // location.href = `${url}/#/sso?username=${encodeURIComponent(username)}&password=${encodeURIComponent(password)}`
+      const aEle = document.createElement('a')
+      aEle.href = `${url}/#/sso?username=${encodeURIComponent(username)}&password=${encodeURIComponent(password)}`
+      aEle.target = '_blank'
+      aEle.click()
+    }
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+>>> .el-col:nth-child(5n + 1) {
+  margin-left: 0;
+}
+>>> .el-col:nth-child(n + 6) {
+  margin-top: 20px;
+}
+.routerCardPar {
+  /*padding: 0 20%;*/
+  width: 900px;
+  margin: 20px auto 0 auto;
+  display: flex;
+  justify-content: flex-start;
+  flex-wrap: wrap;
+  .routerCard {
+    cursor: pointer;
+    width: 200px;
+    display: inline-block;
+    margin-bottom: 20px;
+    &:not(:nth-child(4n)) {
+      margin-right: 30px;
+    }
+
+    ::v-deep .el-card__body {
+      display: flex;
+      flex-direction: column;
+      justify-content: center;
+      align-items: center;
+      img {
+        width: 60px;
+      }
+      span {
+        display: block;
+        margin-top: 15px;
+      }
+    }
+  }
+}
+
+.content {
+  padding: 20px;
+  display: flex;
+  flex-direction: column;
+  justify-content: space-around;
+  align-items: center;
+
+  span {
+    font-size: 16px;
+    font-weight: 600;
+    margin-bottom: 15px;
+  }
+  ::v-deep .el-button {
+    width: 60%;
+  }
+}
+
+.time {
+  font-size: 13px;
+  color: #999;
+}
+
+.bottom {
+  margin-top: 13px;
+  line-height: 12px;
+}
+
+.button {
+  padding: 0;
+  float: right;
+}
+
+.image {
+  width: 100%;
+  display: block;
+}
+
+.clearfix:before,
+.clearfix:after {
+  display: table;
+  content: "";
+}
+
+.clearfix:after {
+  clear: both
+}
+</style>