| | |
| | | <!DOCTYPE html> |
| | | <html> |
| | | |
| | | <head> |
| | | <meta charset="utf-8" /> |
| | | <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" /> |
| | |
| | | } |
| | | </style> |
| | | </head> |
| | | <script src="./src/assets/ddlogin.js"></script> |
| | | <!-- <script src="https://g.alicdn.com/dingding/dinglogin/0.0.5/ddLogin.js"></script> --> |
| | | |
| | | <body> |
| | | <div id="app"> |
| | |
| | | </div> |
| | | <script type="module" src="/src/main.ts"></script> |
| | | </body> |
| | | |
| | | </html> |
| | |
| | | "vue": "3.2.45", |
| | | "vue-cropper": "1.0.3", |
| | | "vue-i18n": "9.2.2", |
| | | "vue-lsp": "^1.0.3", |
| | | "vue-router": "4.1.4", |
| | | "vue-types": "^5.0.3" |
| | | }, |
| | |
| | | |
| | | <script setup lang="ts"> |
| | | import axios from 'axios'; |
| | | import useSettingsStore from '@/store/modules/settings' |
| | | import { handleThemeStyle } from '@/utils/theme' |
| | | import useSettingsStore from '@/store/modules/settings'; |
| | | import { handleThemeStyle } from '@/utils/theme'; |
| | | import useAppStore from '@/store/modules/app'; |
| | | import { createUser } from "@/api/system/oss"; |
| | | import { setToken } from "@/utils/auth"; |
| | | import usePermissionStore from "@/store/modules/permission"; |
| | | import { isHttp } from "@/utils/validate"; |
| | | import { createUser } from '@/api/system/oss'; |
| | | import { setToken, removeToken } from '@/utils/auth'; |
| | | import usePermissionStore from '@/store/modules/permission'; |
| | | import { isHttp } from '@/utils/validate'; |
| | | const appStore = useAppStore(); |
| | | const size = computed(() => appStore.size as any); |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | onMounted(async () => { |
| | | |
| | | await nextTick(() => { |
| | | // 初始化主题样式 |
| | | handleThemeStyle(useSettingsStore().theme) |
| | | }) |
| | | }) |
| | | handleThemeStyle(useSettingsStore().theme); |
| | | }); |
| | | }); |
| | | </script> |
| | |
| | | method: 'get' |
| | | }); |
| | | }; |
| | | |
| | | export const dingdingLogin=(data: any ): AxiosPromise<String> => { |
| | | return request({ |
| | | url: '/auth/dingdingLogin', |
| | | method: 'get', |
| | | params: data |
| | | }) |
| | | } |
| | | export default { |
| | | listUser, |
| | | getUser, |
| | |
| | | getAuthRole, |
| | | updateAuthRole, |
| | | deptTreeSelect, |
| | | listUserByDeptId |
| | | listUserByDeptId, |
| | | dingdingLogin |
| | | }; |
New file |
| | |
| | | ! function (e) { |
| | | var t = {}; |
| | | |
| | | function r(n) { |
| | | if (t[n]) return t[n].exports; |
| | | var o = t[n] = { |
| | | i: n, |
| | | l: !1, |
| | | exports: {} |
| | | }; |
| | | return e[n].call(o.exports, o, o.exports, r), o.l = !0, o.exports |
| | | } |
| | | r.m = e, r.c = t, r.d = function (e, t, n) { |
| | | r.o(e, t) || Object.defineProperty(e, t, { |
| | | enumerable: !0, |
| | | get: n |
| | | }) |
| | | }, r.r = function (e) { |
| | | "undefined" != typeof Symbol && Symbol.toStringTag && Object.defineProperty(e, Symbol.toStringTag, { |
| | | value: "Module" |
| | | }), Object.defineProperty(e, "__esModule", { |
| | | value: !0 |
| | | }) |
| | | }, r.t = function (e, t) { |
| | | if (1 & t && (e = r(e)), 8 & t) return e; |
| | | if (4 & t && "object" == typeof e && e && e.__esModule) return e; |
| | | var n = Object.create(null); |
| | | if (r.r(n), Object.defineProperty(n, "default", { |
| | | enumerable: !0, |
| | | value: e |
| | | }), 2 & t && "string" != typeof e) |
| | | for (var o in e) r.d(n, o, function (t) { |
| | | return e[t] |
| | | }.bind(null, o)); |
| | | return n |
| | | }, r.n = function (e) { |
| | | var t = e && e.__esModule ? function () { |
| | | return e.default |
| | | } : function () { |
| | | return e |
| | | }; |
| | | return r.d(t, "a", t), t |
| | | }, r.o = function (e, t) { |
| | | return Object.prototype.hasOwnProperty.call(e, t) |
| | | }, r.p = "", r(r.s = 1382) |
| | | }({ |
| | | 1382: function (e, t) { |
| | | var r = function (e, t) { |
| | | var r = e.match(new RegExp("[?&]" + t + "=([^&]+)")); |
| | | return r ? r[1] : null |
| | | }; |
| | | window.DTFrameLogin = function (e, t, n, o) { |
| | | var i, u = e.id && document.getElementById(e.id) || null, |
| | | c = document.createElement("iframe"); |
| | | t.client_id && t.redirect_uri && t.response_type && t.scope ? u ? (u.innerHTML = "", u.appendChild(c), c && c.contentWindow && c.contentWindow.postMessage && window.addEventListener ? (c.src = "https://" + ((i = t).isPre ? "pre-login" : "login") + ".dingtalk.com/oauth2/auth?iframe=true&redirect_uri=" + i.redirect_uri + "&response_type=" + i.response_type + "&client_id=" + i.client_id + "&scope=" + i.scope + (i.prompt ? "&prompt=" + i.prompt : "") + (i.state ? "&state=" + i.state : "") + (i.org_type ? "&org_type=" + i.org_type : "") + (i.corpId ? "&corpId=" + i.corpId : "") + (i.exclusiveLogin ? "&exclusiveLogin=" + i.exclusiveLogin : "") + (i.exclusiveCorpId ? "&exclusiveCorpId=" + i.exclusiveCorpId : ""), c.width = "" + (e.width || 300), c.height = "" + (e.height || 300), c.frameBorder = "0", c.scrolling = "no", window.addEventListener("message", (function (e) { |
| | | var t = e.data, |
| | | i = e.origin; |
| | | if (/login\.dingtalk\.com/.test(i) && t) |
| | | if (t.success && t.redirectUrl) { |
| | | var u = t.redirectUrl, |
| | | c = r(u, "authCode") || "", |
| | | d = r(u, "state") || "", |
| | | s = r(u, "error") || ""; |
| | | c ? n && n({ |
| | | redirectUrl: u, |
| | | authCode: c, |
| | | state: d |
| | | }) : o && o(s) |
| | | } else o && o(t.errorMsg) |
| | | }))) : o && o("Browser not support")) : o && o("Element not found") : o && o("Missing parameters") |
| | | } |
| | | } |
| | | }); |
| | |
| | | import useSettingsStore from '@/store/modules/settings'; |
| | | import usePermissionStore from '@/store/modules/permission'; |
| | | import { ElMessage } from "element-plus"; |
| | | import { fa } from 'element-plus/es/locale'; |
| | | |
| | | NProgress.configure({ showSpinner: false }); |
| | | const whiteList = ['/login', '/register', '/social-callback']; |
| | | |
| | | router.beforeEach(async (to, from, next) => { |
| | | NProgress.start(); |
| | | if (getToken()) { |
| | | |
| | | if (judge(getToken())) { |
| | | console.log('判断当前用户是否已拉取完user_info信息'); |
| | | to.meta.title && useSettingsStore().setTitle(to.meta.title as string); |
| | | |
| | | /* has token*/ |
| | | if (to.path === '/login') { |
| | | next({ path: '/' }); |
| | | NProgress.done(); |
| | | } else { |
| | | if (useUserStore().roles.length === 0) { |
| | | // if (useUserStore().roles.length === 0) { |
| | | isRelogin.show = true; |
| | | // 判断当前用户是否已拉取完user_info信息 |
| | | // // 判断当前用户是否已拉取完user_info信息 |
| | | |
| | | const [err] = await tos(useUserStore().getInfo()); |
| | | if (err) { |
| | | await useUserStore().logout(); |
| | | ElMessage.error(err); |
| | | next({ path: '/' }); |
| | | } else { |
| | | isRelogin.show = false; |
| | | const accessRoutes = await usePermissionStore().generateRoutes(); |
| | | // 根据roles权限生成可访问的路由表 |
| | | accessRoutes.forEach((route) => { |
| | | if (!isHttp(route.path)) { |
| | | router.addRoute(route); // 动态添加可访问路由表 |
| | | } |
| | | }); |
| | | next({ ...to, replace: true }); // hack方法 确保addRoutes已完成 |
| | | } |
| | | } else { |
| | | // const [err] = await tos(useUserStore().getInfo()); |
| | | // if (err) { |
| | | // await useUserStore().logout(); |
| | | // ElMessage.error(err); |
| | | // next({ path: '/' }); |
| | | // } else { |
| | | // isRelogin.show = false; |
| | | // const accessRoutes = await usePermissionStore().generateRoutes(); |
| | | // // 根据roles权限生成可访问的路由表 |
| | | // accessRoutes.forEach((route) => { |
| | | // if (!isHttp(route.path)) { |
| | | // router.addRoute(route); // 动态添加可访问路由表 |
| | | // } |
| | | // }); |
| | | // next({ ...to, replace: true }); // hack方法 确保addRoutes已完成 |
| | | // } |
| | | // } else { |
| | | next(); |
| | | } |
| | | // } |
| | | } |
| | | } else { |
| | | // 没有token |
| | |
| | | router.afterEach(() => { |
| | | NProgress.done(); |
| | | }); |
| | | |
| | | const judge = (token: string) => { |
| | | if (token) { |
| | | var data = JSON.parse(token) |
| | | if (data != null) { |
| | | if (data.expirse != null && new Date().getTime() - data.expirse < 60 * 60 * 1000) { |
| | | return true |
| | | } |
| | | } |
| | | } |
| | | return false |
| | | } |
| | |
| | | }, |
| | | { |
| | | path: '/login', |
| | | component: () => import('@/views/login.vue'), |
| | | component: () => import('@/views/dingdingLogin.vue'), |
| | | hidden: true |
| | | }, |
| | | { |
| | | path: '/dingdingLogin', |
| | | component: () => import('@/views/dingdingLogin.vue'), |
| | | hidden: true |
| | | }, |
| | | { |
New file |
| | |
| | | <template> |
| | | <div id="content" class="content"> |
| | | <div> |
| | | <div style="text-align:center">钉钉扫码登录</div> |
| | | <div id="self_defined_element" class="self-defined-classname"></div> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | |
| | | <script setup name="Oss" lang="ts"> |
| | | import { useRoute } from 'vue-router'; |
| | | import { dingdingLogin } from '@/api/system/user'; |
| | | const getUserDate = async (code: string) => { |
| | | // await dingdingLogin({ |
| | | // authCode: code |
| | | // }).then((res: any) => { |
| | | // this.$router.push('/student'); |
| | | // }); |
| | | }; |
| | | onMounted(() => { |
| | | const route = useRoute(); |
| | | let code = route.query.code; |
| | | if (code) { |
| | | getUserDate(code); |
| | | } else { |
| | | // STEP3:在需要的时候,调用 window.DTFrameLogin 方法构造登录二维码,并处理登录成功或失败的回调。 |
| | | window.DTFrameLogin( |
| | | { |
| | | id: 'self_defined_element', |
| | | width: 300, |
| | | height: 300 |
| | | }, |
| | | { |
| | | redirect_uri: encodeURIComponent('https://f060-183-223-248-101.ngrok-free.app/auth/dingdingLogin'), |
| | | client_id: 'dingl5dxahaj3uzfug66', |
| | | scope: 'openid', |
| | | response_type: 'code', |
| | | state: 'STATE', |
| | | prompt: 'consent' |
| | | }, |
| | | (loginResult: any) => { |
| | | console.log('loginResult:' + loginResult); |
| | | |
| | | debugger; |
| | | const { redirectUrl, authCode, state } = loginResult; |
| | | // 这里可以直接进行重定向 |
| | | window.location.href = redirectUrl; |
| | | // 也可以在不跳转页面的情况下,使用code进行授权 |
| | | console.log(authCode); |
| | | }, |
| | | (errorMsg: any) => { |
| | | // 这里一般需要展示登录失败的具体原因,可以使用toast等轻提示 |
| | | console.error(`errorMsg of errorCbk: ${errorMsg}`); |
| | | } |
| | | ); |
| | | } |
| | | }); |
| | | </script> |
| | | |
| | | <style lang="scss" scoped> |
| | | .content { |
| | | display: flex; |
| | | align-items: center; |
| | | justify-content: center; |
| | | } |
| | | .self-defined-classname { |
| | | // width: 300px; |
| | | // height: 300px; |
| | | } |
| | | </style> |
New file |
| | |
| | | <template> |
| | | <div id="content" class="content"> |
| | | <!-- <div> |
| | | <div style="text-align:center">钉钉扫码登录</div> |
| | | <div id="self_defined_element" class="self-defined-classname"></div> |
| | | </div> --> |
| | | </div> |
| | | </template> |
| | | <script setup name="Oss" lang="ts"> |
| | | import { useRoute } from 'vue-router'; |
| | | import { dingdingLogin } from '@/api/system/user'; |
| | | import { setToken } from '@/utils/auth'; |
| | | |
| | | const getUserDate = async (authCode: string, code: string) => { |
| | | await dingdingLogin({ |
| | | authCode: authCode, |
| | | code: code |
| | | }).then((res: any) => { |
| | | var data = { value: 'admin', expirse: new Date().getTime() }; |
| | | |
| | | setToken(JSON.stringify(data)); |
| | | window.location.href = '/index'; |
| | | }); |
| | | }; |
| | | onMounted(() => { |
| | | const router = useRoute(); |
| | | let code = router.query.code; |
| | | let authCode = router.query.authCode; |
| | | if (code) { |
| | | getUserDate(authCode, code); |
| | | } else { |
| | | window.location.href = |
| | | 'https://login.dingtalk.com/oauth2/auth?redirect_uri=http://127.0.0.1:81/login&response_type=code&client_id=dingl5dxahaj3uzfug66&scope=oD9LphDV7Ge4vGgnIiS3WIwiEiE&state=dddd&prompt=consent'; |
| | | // // STEP3:在需要的时候,调用 window.DTFrameLogin 方法构造登录二维码,并处理登录成功或失败的回调。 |
| | | // window.DTFrameLogin( |
| | | // { |
| | | // id: 'self_defined_element', |
| | | // width: 300, |
| | | // height: 300 |
| | | // }, |
| | | // { |
| | | // redirect_uri: encodeURIComponent('http://127.0.0.1:8080/auth/dingdingLogin'), |
| | | // client_id: 'dingl5dxahaj3uzfug66', |
| | | // scope: 'openid', |
| | | // response_type: 'code', |
| | | // state: 'STATE', |
| | | // prompt: 'consent' |
| | | // }, |
| | | // (loginResult: any) => { |
| | | // console.log('loginResult:' + loginResult); |
| | | |
| | | // const { redirectUrl, authCode, state } = loginResult; |
| | | // // 这里可以直接进行重定向 |
| | | // window.location.href = redirectUrl; |
| | | // // 也可以在不跳转页面的情况下,使用code进行授权 |
| | | // console.log(authCode); |
| | | // }, |
| | | // (errorMsg: any) => { |
| | | // // 这里一般需要展示登录失败的具体原因,可以使用toast等轻提示 |
| | | // console.error(`errorMsg of errorCbk: ${errorMsg}`); |
| | | // } |
| | | // ); |
| | | } |
| | | }); |
| | | </script> |
| | | |
| | | <style lang="scss" scoped> |
| | | .content { |
| | | display: flex; |
| | | align-items: center; |
| | | justify-content: center; |
| | | } |
| | | .self-defined-classname { |
| | | // width: 300px; |
| | | // height: 300px; |
| | | } |
| | | </style> |
| | |
| | | // } catch (error) { |
| | | // console.log(error); |
| | | // } |
| | | router.push('index') |
| | | // router.push('index') |
| | | |
| | | }); |
| | | </script> |
| | |
| | | [env.VITE_APP_BASE_API]: { |
| | | // target: 'http://162.14.79.111:2023', |
| | | // target: 'http://172.35.50.34:8080', |
| | | target: 'http://192.168.3.228:8080', |
| | | target: 'http://127.0.0.1:8080', |
| | | changeOrigin: true, |
| | | rewrite: (path) => path.replace(new RegExp('^' + env.VITE_APP_BASE_API), '') |
| | | } |