@utogether/udp-core 1.0.1-beta.12 → 1.0.1-beta.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (72) hide show
  1. package/dist/{403-D7L5zm05.js → 403-CYdgejwn.js} +1 -1
  2. package/dist/{404-BQKzkK5W.js → 404-CblgDc5z.js} +1 -1
  3. package/dist/{500-BM6k8XR5.js → 500-BZ6wCwWc.js} +1 -1
  4. package/dist/{AuthorityInfo-Dc-7W4L_.js → AuthorityInfo-C7ssheq6.js} +1 -1
  5. package/dist/{AuthorityInfo.vue_vue_type_style_index_0_lang-CKvlh3lm.js → AuthorityInfo.vue_vue_type_style_index_0_lang-DiFYQyk8.js} +1 -1
  6. package/dist/{Company-BgwMUr-I.js → Company-ECS1Fe1S.js} +3 -3
  7. package/dist/{CompanyPanel-CDfVCPKC.js → CompanyPanel-Bka7k-uP.js} +1 -1
  8. package/dist/{Department-CFvEB4Ys.js → Department-DGKkYUdS.js} +3 -3
  9. package/dist/{DepartmentPanel-11Ytcj2u.js → DepartmentPanel-C17CZmjl.js} +1 -1
  10. package/dist/{DesignPanel-CP8z6teZ.js → DesignPanel-BWvmkPpc.js} +1 -1
  11. package/dist/{DesignPanel.vue_vue_type_style_index_0_lang-Cp-WR8yE.js → DesignPanel.vue_vue_type_style_index_0_lang-CIrAgdYO.js} +2 -2
  12. package/dist/{DictView-13NoDgPW.js → DictView-B969z8wA.js} +1 -1
  13. package/dist/{InvOrganization-DOD4QdEX.js → InvOrganization-6bVuN-NP.js} +4 -2
  14. package/dist/{Org-cezJs-6P.js → Org-kNkuyf89.js} +1 -1
  15. package/dist/{Preview-DzOKwnp8.js → Preview-CNn9UAsy.js} +1 -1
  16. package/dist/{ReportDefine-DWJq2q0f.js → ReportDefine-Cjv4aRVy.js} +1 -1
  17. package/dist/{ReportDesign-f_ed8u_q.js → ReportDesign-BrCobVSd.js} +2 -2
  18. package/dist/{ReportQuery-D58gv_yZ.js → ReportQuery-Gr87UX2I.js} +1 -1
  19. package/dist/{ReportQueryFrom-R0R6EbYv.js → ReportQueryFrom-CX6cb9GY.js} +1 -1
  20. package/dist/{ReportQueryFrom.vue_vue_type_style_index_0_lang-CIFpgUAH.js → ReportQueryFrom.vue_vue_type_style_index_0_lang-Dz3ZapUS.js} +1 -1
  21. package/dist/{ReportTemplate-BTknctTT.js → ReportTemplate-BDRw8aY4.js} +1 -1
  22. package/dist/{Role-QTDJ16h8.js → Role-B2uHACAG.js} +3 -3
  23. package/dist/{RoleAssign-7aZ3ufp5.js → RoleAssign-Cpwz3ZND.js} +3 -3
  24. package/dist/{RolePanel-XXwmaAgy.js → RolePanel-0G7e5LC8.js} +1 -1
  25. package/dist/{RolePanel-CSe-UoR5.js → RolePanel-CHlQBMqq.js} +1 -1
  26. package/dist/{RolePanel.vue_vue_type_script_setup_true_lang-kConrKpo.js → RolePanel.vue_vue_type_script_setup_true_lang-C_vBaRyr.js} +3 -3
  27. package/dist/{RolePanel.vue_vue_type_script_setup_true_lang-BsNhkvFo.js → RolePanel.vue_vue_type_script_setup_true_lang-Cuyr3Z0F.js} +1 -1
  28. package/dist/{ScrollPanel.vue_vue_type_style_index_0_lang-DtaqM_iA.js → ScrollPanel.vue_vue_type_style_index_0_lang-B_W_v3j5.js} +1 -1
  29. package/dist/{Staff-BsREgfrQ.js → Staff-BALciFZu.js} +3 -3
  30. package/dist/{StaffInfo-CQtVXfvS.js → StaffInfo-BNzGN-gJ.js} +1 -1
  31. package/dist/{StaffInfo.vue_vue_type_script_setup_true_lang-BRRtcGIH.js → StaffInfo.vue_vue_type_script_setup_true_lang-BSYVizqX.js} +1 -1
  32. package/dist/{StaffPanel-cQTAulcP.js → StaffPanel-xWUgRJqR.js} +1 -1
  33. package/dist/{StaffPanel.vue_vue_type_script_setup_true_lang-BLeXlrI1.js → StaffPanel.vue_vue_type_script_setup_true_lang-duZSwgoN.js} +2 -2
  34. package/dist/{SysUser-DN5_46io.js → SysUser-q114FdeD.js} +2 -2
  35. package/dist/{SysUserPanel-DTBNR42y.js → SysUserPanel-CognKMl5.js} +1 -1
  36. package/dist/{SysUserPanel.vue_vue_type_script_setup_true_lang-CF2pHcPP.js → SysUserPanel.vue_vue_type_script_setup_true_lang-CMbUdk6A.js} +1 -1
  37. package/dist/{SystemMenu-D9TKZwgb.js → SystemMenu-DVGGSkBO.js} +2 -2
  38. package/dist/{UserInfo-DJ5LRTMe.js → UserInfo-Dug8S6IS.js} +1 -1
  39. package/dist/{UserInfo.vue_vue_type_style_index_0_lang-CIpPef_S.js → UserInfo.vue_vue_type_style_index_0_lang-GUvWUfH6.js} +1 -1
  40. package/dist/{childView-CGZSd19y.js → childView-DC4St5Yu.js} +1 -1
  41. package/dist/{childView-DrL_Qi-q.js → childView-DgwW1_pS.js} +1 -1
  42. package/dist/{childView.vue_vue_type_style_index_0_lang-D2AzjPNV.js → childView.vue_vue_type_style_index_0_lang-C6ns1H7X.js} +1 -1
  43. package/dist/{childView.vue_vue_type_style_index_0_lang-B8wEeuFX.js → childView.vue_vue_type_style_index_0_lang-CHB4aljD.js} +1 -1
  44. package/dist/{code-rule-DVEoh1Z4.js → code-rule-DrnZAXq6.js} +1 -1
  45. package/dist/core.es.js +1 -1
  46. package/dist/{cron-task-BBpccUV_.js → cron-task-8TSn9qgc.js} +1 -1
  47. package/dist/{frameView-Cw6_EqfJ.js → frameView-DsJ7Niwn.js} +1 -1
  48. package/dist/index-ChmJT--N.js +2618 -0
  49. package/dist/{layoutView-CL2Ef3bw.js → layoutView-JchyMwjZ.js} +2 -2
  50. package/dist/{login-BDocwo7t.js → login-BXkivLFZ.js} +34 -33
  51. package/dist/{lov-view-R8nnUEbA.js → lov-view-Ck-gMZAO.js} +2 -2
  52. package/dist/{menuInfo-B-nGOcSv.js → menuInfo-u432VWl_.js} +1 -1
  53. package/dist/{menuInfo.vue_vue_type_style_index_0_lang-1VuzxMb0.js → menuInfo.vue_vue_type_style_index_0_lang-JMkwMJ9n.js} +1 -1
  54. package/dist/{pda-app-D5wBClj0.js → pda-app-BeqyF-LQ.js} +1 -1
  55. package/dist/{resource-BXGSsXzw.js → resource-DkNbG8D8.js} +1 -1
  56. package/dist/{su-welcome-DISZAkBB.js → su-welcome-DEVHyaQ4.js} +1 -1
  57. package/dist/{sys-config-DuyYdzXL.js → sys-config-8MIo11zU.js} +1 -1
  58. package/dist/udp-core.css +2 -2
  59. package/dist/{utogether-C2KGHvut.js → utogether-N0mpFm7j.js} +1 -1
  60. package/package.json +18 -18
  61. package/src/api/http.ts +1 -4
  62. package/src/api/index.ts +33 -31
  63. package/src/api/user.ts +2 -2
  64. package/src/main.ts +3 -9
  65. package/src/router/index.ts +177 -177
  66. package/src/style/vxetable.scss +1 -1
  67. package/src/utils/propTypes.ts +42 -42
  68. package/src/utils/udp/http/index.ts +19 -8
  69. package/src/views/login/login-view.vue +300 -300
  70. package/src/views/organization/inv-org/InvOrganization.vue +68 -68
  71. package/src/views/ulogin/login.vue +4 -3
  72. package/dist/index-BAkwQh8m.js +0 -4467
@@ -74,12 +74,12 @@ class SuHttp {
74
74
  if (whiteList.some(v => config.url.indexOf(v) > -1)) return config;
75
75
  return new Promise(resolve => {
76
76
  const token = cookies.get(kTOKENKEY);
77
- // debugger;
78
77
  if (token) {
79
78
  const data = JSON.parse(token);
80
79
  const now = new Date().getTime();
81
80
  const expired = data.expires - now <= 0;
82
81
  if (expired) {
82
+ debugger;
83
83
  if (!SuHttp.isRefreshing) {
84
84
  SuHttp.isRefreshing = true;
85
85
  // requests.push(() => SuHttp.axiosInstance(config));
@@ -87,17 +87,28 @@ class SuHttp {
87
87
  refreshToken: data.refreshToken
88
88
  })
89
89
  .then((res: any) => {
90
- // 替换token
91
- this.setToken(res);
92
- config.headers['Authorization'] = 'Bearer ' + res.access_token;
93
- // token 刷新后将数组的方法重新执行
94
- // @ts-ignore
95
- SuHttp.requests.forEach(cb => cb(res.access_token));
90
+ if (!res?.access_token) {
91
+ SuHttp.requests = []; // 重新请求完清空
92
+ cookies.remove('kCookies_token');
93
+ cookies.remove('authorized-token');
94
+ cookies.remove('loginer');
95
+ this.router.push({ name: 'login' });
96
+ } else {
97
+ // 替换token
98
+ this.setToken(res);
99
+ config.headers['Authorization'] = 'Bearer ' + res.access_token;
100
+ // token 刷新后将数组的方法重新执行
101
+ // @ts-ignore
102
+ SuHttp.requests.forEach(cb => cb(res.access_token));
103
+ }
104
+ })
105
+ .catch(e => {
106
+ console.log({ e });
96
107
  SuHttp.requests = []; // 重新请求完清空
108
+ this.router.push({ name: 'login' });
97
109
  })
98
110
  .finally(() => {
99
111
  SuHttp.isRefreshing = false;
100
- this.router.push({ name: 'login' });
101
112
  });
102
113
  }
103
114
  // @ts-ignore
@@ -1,300 +1,300 @@
1
- <template>
2
- <div class="select-none">
3
- <div class="absolute flex justify-center items-center right-5 top-3">
4
- <!-- 主题 -->
5
- <!-- <el-switch
6
- v-model="dataTheme"
7
- inline-prompt
8
- :active-icon="dayIcon"
9
- :inactive-icon="darkIcon"
10
- @change="dataThemeChange"
11
- /> -->
12
- <!-- 国际化 -->
13
- <!-- <el-dropdown v-if="sysConfig['i18nEnabled'] === 'Y'" trigger="click">
14
- <globalization
15
- class="hover:text-primary hover:!bg-[transparent] w-[20px] h-[20px] ml-1.5 cursor-pointer outline-hidden duration-300"
16
- />
17
- <template #dropdown>
18
- <el-dropdown-menu class="translation">
19
- <el-dropdown-item
20
- :style="getDropdownItemStyle(locale, 'zh')"
21
- :class="['dark:text-white!', getDropdownItemClass(locale, 'zh')]"
22
- @click="translationCh"
23
- >
24
- <IconifyIconOffline v-show="locale === 'zh'" class="check-zh" :icon="ri:check-line" />
25
- 简体中文
26
- </el-dropdown-item>
27
- <el-dropdown-item
28
- :style="getDropdownItemStyle(locale, 'en')"
29
- :class="['dark:text-white!', getDropdownItemClass(locale, 'en')]"
30
- @click="translationEn"
31
- >
32
- <span v-show="locale === 'en'" class="check-en">
33
- <IconifyIconOffline :icon="ri:check-line" />
34
- </span>
35
- English
36
- </el-dropdown-item>
37
- </el-dropdown-menu>
38
- </template>
39
- </el-dropdown> -->
40
- </div>
41
- <div class="login-container">
42
- <div class="bg-img" :style="{ backgroundImage: `url(${sysConfig['backgroundImg']}` }" />
43
- <div class="login-box">
44
- <div class="login-form">
45
- <img v-if="sysConfig['logo']" class="login-logo-img" :src="sysConfig['logo']" />
46
- <Motion v-if="sysConfig['title']">
47
- <h2 class="outline-hidden">
48
- <TypeIt :values="[sysConfig['title']]" :cursor="false" :speed="150" />
49
- </h2>
50
- </Motion>
51
-
52
- <el-form ref="ruleFormRef" :model="ruleForm" :rules="loginRules" size="large">
53
- <Motion :delay="100">
54
- <el-form-item
55
- :rules="[{ required: true, message: $t('message.username'), trigger: 'blur' }]"
56
- prop="username"
57
- >
58
- <el-input v-model.trim="ruleForm.username" autofocus clearable :prefix-icon="useRenderIcon(User)" />
59
- </el-form-item>
60
- </Motion>
61
-
62
- <Motion :delay="150">
63
- <el-form-item prop="passWord">
64
- <el-input v-model="ruleForm.passWord" clearable show-password :prefix-icon="useRenderIcon(Lock)" />
65
- </el-form-item>
66
- </Motion>
67
- <Motion :delay="250">
68
- <el-form-item>
69
- <el-button
70
- class="w-full mt-4"
71
- size="default"
72
- type="primary"
73
- :loading="loading"
74
- @click="onLogin(ruleFormRef)"
75
- >
76
- {{ $t('message.udp.login') }}
77
- </el-button>
78
- </el-form-item>
79
- </Motion>
80
- </el-form>
81
- </div>
82
- <div class="fixed text-xs text-gray-500 bottom-4">Copyright ©2021{{ sysConfig['copyright'] }}版权所有</div>
83
- </div>
84
- </div>
85
- </div>
86
- </template>
87
-
88
- <script setup lang="ts">
89
- import { ref, reactive, onMounted, onBeforeMount, onBeforeUnmount } from 'vue';
90
- import { useRouter } from 'vue-router';
91
- import type { FormInstance } from 'element-plus';
92
- import { storageLocal, cookies, successMessage, delay } from '@utogether/utils';
93
- import { toDateString } from 'xe-utils';
94
- import to from 'await-to-js';
95
-
96
- import Motion from './utils/motion';
97
- import { loginRules } from './utils/rule';
98
- import TypeIt from '@/components/SuTypeit';
99
- import { useRenderIcon } from '@/components/ReIcon/src/hooks';
100
- // import { useTranslationLang } from '@/layout/hooks/useTranslationLang';
101
- import { useLayout } from '@/layout/hooks/useLayout';
102
- // import { useNav } from '@/layout/hooks/useNav';
103
- // import { useDataThemeChange } from '@/layout/hooks/useDataThemeChange';
104
- import { useSystemStoreHook } from '@/store/modules/system';
105
-
106
- import { getServiceApi } from '../../api';
107
- import { initDict } from '../../api/user';
108
- import { getPlatform, getBrower } from '@/utils/browers';
109
- // import dayIcon from '@/assets/svg/day.svg?component';
110
- // import darkIcon from '@/assets/svg/dark.svg?component';
111
- // import globalization from '@/assets/svg/globalization.svg?component';
112
- import Lock from '@iconify-icons/ri/lock-fill';
113
- import User from '@iconify-icons/ri/user-3-fill';
114
-
115
- defineOptions({ name: 'LoginView' });
116
-
117
- interface IRSAPublic {
118
- publicKeyExponent: string;
119
- publicKeyModulus: string;
120
- requestKey: string;
121
- }
122
-
123
- const router = useRouter();
124
-
125
- // const bgStyle = ref({});
126
- const sysConfig = ref({});
127
- const loading = ref(false);
128
- const ruleFormRef = ref<FormInstance>();
129
-
130
- const serviceApi = getServiceApi();
131
-
132
- const { initStorage } = useLayout();
133
- initStorage();
134
- // const { dataTheme, dataThemeChange } = useDataThemeChange();
135
- // dataThemeChange();
136
- // const { getDropdownItemStyle, getDropdownItemClass } = useNav();
137
- // const { locale, translationCh, translationEn } = useTranslationLang();
138
-
139
- const ruleForm = reactive({
140
- username: '',
141
- passWord: ''
142
- });
143
-
144
- const publicRSA: IRSAPublic = reactive({
145
- publicKeyExponent: '10001',
146
- publicKeyModulus:
147
- 'a12708ab26367e1711bd767f6bb1f29afbd85380185723d7b492230e2567c95cf5718eca745da0643400ca619fbeec892df61abe1f71ad3b822d076ed831080c53782edf8c0627ee95c57e2bee12fe55da2b3cadec59947a75ccccbbf36fb3b781c93b4bf51489789f1c0849f9023a16ec70bef41a504785e1082b6f13588e29',
148
- requestKey: ''
149
- });
150
-
151
- const onLogin = async (formEl: FormInstance | undefined) => {
152
- if (!formEl) return;
153
- await formEl.validate(valid => {
154
- if (valid) {
155
- loading.value = true;
156
- const { username, passWord } = ruleForm;
157
-
158
- // @ts-ignore
159
- setMaxDigits(200);
160
- // @ts-ignore
161
- const rsakeypair = new RSAKeyPair(publicRSA.publicKeyExponent, '', publicRSA.publicKeyModulus);
162
- // @ts-ignore
163
- const password = encryptedString(rsakeypair, passWord.split('').reverse().join(''));
164
- const param = {
165
- username,
166
- password,
167
- requestKey: publicRSA.requestKey,
168
- domain: window.location.origin
169
- };
170
- serviceApi
171
- .post('/uath/login', param)
172
- .then(async (data: IResponseData) => {
173
- successMessage(`👏 恭喜,成功登录${sysConfig.value['title']}!!!🎉`);
174
- useSystemStoreHook().setSessionKey(data);
175
- cacheToken(data);
176
- cookies.set('loginer', username);
177
- if (!storageLocal.getItem('kLov')) {
178
- initDict().then(res => useSystemStoreHook().setDict(res));
179
- }
180
- await delay(300);
181
- router.push('/');
182
- await insertLoginInfo(username);
183
- })
184
- .finally(() => {
185
- loading.value = false;
186
- });
187
- }
188
- });
189
- };
190
-
191
- /**
192
- * @description: 缓存token
193
- * @param {*} token token数据
194
- * @return {*}
195
- */
196
- const cacheToken = token => {
197
- const { access_token, expires_in, refresh_token } = token;
198
- const cache = {
199
- accessToken: access_token,
200
- refreshToken: refresh_token,
201
- expires: Date.now() + expires_in * 1000
202
- };
203
- const kTOKENKEY = 'authorized-token';
204
-
205
- cookies.set('kCookies_token', token.access_token);
206
- const dataString = JSON.stringify(cache);
207
- expires_in > 0 ? cookies.set(kTOKENKEY, dataString) : cookies.set(kTOKENKEY, dataString);
208
- };
209
-
210
- const insertLoginInfo = username => {
211
- const userAgent = navigator.userAgent.toLowerCase();
212
- const { browser, browserVersion } = getBrower(userAgent);
213
- const obj = {
214
- userName: username,
215
- loginTime: toDateString(new Date()),
216
- browser,
217
- browserVersion,
218
- operatingSystem: getPlatform(userAgent)
219
- };
220
- serviceApi.post('/upfm/v1/userMonitor', obj);
221
- };
222
-
223
- /** 使用公共函数,避免`removeEventListener`失效 */
224
- function onkeypress({ code }: KeyboardEvent) {
225
- if (['Enter', 'NumpadEnter'].includes(code)) {
226
- onLogin(ruleFormRef.value);
227
- }
228
- }
229
-
230
- onMounted(() => {
231
- window.document.addEventListener('keypress', onkeypress);
232
- });
233
-
234
- onBeforeUnmount(() => {
235
- window.document.removeEventListener('keypress', onkeypress);
236
- });
237
- /**
238
- * @description: 获取系统配置
239
- * @return {*}
240
- */
241
- const getSysConfig = async () => {
242
- const [err, data]: [Error, any] = await to(serviceApi.get('/upfm/v1/sysConfig', {}));
243
- if (!err) {
244
- const config = {};
245
- data.list?.forEach(item => {
246
- config[item.configCode] = item.configValue;
247
- if (item.fileName) {
248
- config[item.configCode] = window.location.origin + '/ufil' + item.configValue;
249
- }
250
- });
251
- const env = process.env.NODE_ENV;
252
- const title = data.list?.find(f => f.configCode === `${env}Title` || f.configCode === 'title')?.configValue;
253
- config['title'] = title || 'U-DP';
254
- sysConfig.value = config;
255
- setFavicon();
256
- storageLocal.setItem('kSysConfig', config);
257
- }
258
- };
259
-
260
- const setFavicon = () => {
261
- let favicon = document.querySelector('link[rel="icon"]') as HTMLElement;
262
- // console.log('app', favicon)
263
- if (favicon !== null) {
264
- favicon['href'] = sysConfig.value['favicon'] || '../../../public/favicon.ico';
265
- } else {
266
- favicon = document.createElement('link');
267
- favicon['rel'] = 'icon';
268
- favicon['href'] = sysConfig.value['favicon'] || '../../../public/favicon.ico';
269
- document.head.appendChild(favicon);
270
- }
271
- };
272
-
273
- onBeforeMount(() => {
274
- getSysConfig();
275
- });
276
- </script>
277
-
278
- <style scoped>
279
- @import url('@/style/login2.css');
280
-
281
- /* .translation {
282
- ::v-deep(.el-dropdown-menu__item) {
283
- padding: 5px 40px;
284
- }
285
- } */
286
-
287
- .check-zh {
288
- position: absolute;
289
- left: 20px;
290
- }
291
-
292
- .check-en {
293
- position: absolute;
294
- left: 20px;
295
- }
296
-
297
- :deep(.el-input-group__append, .el-input-group__prepend) {
298
- padding: 0;
299
- }
300
- </style>
1
+ <template>
2
+ <div class="select-none">
3
+ <div class="absolute flex justify-center items-center right-5 top-3">
4
+ <!-- 主题 -->
5
+ <!-- <el-switch
6
+ v-model="dataTheme"
7
+ inline-prompt
8
+ :active-icon="dayIcon"
9
+ :inactive-icon="darkIcon"
10
+ @change="dataThemeChange"
11
+ /> -->
12
+ <!-- 国际化 -->
13
+ <!-- <el-dropdown v-if="sysConfig['i18nEnabled'] === 'Y'" trigger="click">
14
+ <globalization
15
+ class="hover:text-primary hover:!bg-[transparent] w-[20px] h-[20px] ml-1.5 cursor-pointer outline-hidden duration-300"
16
+ />
17
+ <template #dropdown>
18
+ <el-dropdown-menu class="translation">
19
+ <el-dropdown-item
20
+ :style="getDropdownItemStyle(locale, 'zh')"
21
+ :class="['dark:text-white!', getDropdownItemClass(locale, 'zh')]"
22
+ @click="translationCh"
23
+ >
24
+ <IconifyIconOffline v-show="locale === 'zh'" class="check-zh" :icon="ri:check-line" />
25
+ 简体中文
26
+ </el-dropdown-item>
27
+ <el-dropdown-item
28
+ :style="getDropdownItemStyle(locale, 'en')"
29
+ :class="['dark:text-white!', getDropdownItemClass(locale, 'en')]"
30
+ @click="translationEn"
31
+ >
32
+ <span v-show="locale === 'en'" class="check-en">
33
+ <IconifyIconOffline :icon="ri:check-line" />
34
+ </span>
35
+ English
36
+ </el-dropdown-item>
37
+ </el-dropdown-menu>
38
+ </template>
39
+ </el-dropdown> -->
40
+ </div>
41
+ <div class="login-container">
42
+ <div class="bg-img" :style="{ backgroundImage: `url(${sysConfig['backgroundImg']}` }" />
43
+ <div class="login-box">
44
+ <div class="login-form">
45
+ <img v-if="sysConfig['logo']" class="login-logo-img" :src="sysConfig['logo']" />
46
+ <Motion v-if="sysConfig['title']">
47
+ <h2 class="outline-hidden">
48
+ <TypeIt :values="[sysConfig['title']]" :cursor="false" :speed="150" />
49
+ </h2>
50
+ </Motion>
51
+
52
+ <el-form ref="ruleFormRef" :model="ruleForm" :rules="loginRules" size="large">
53
+ <Motion :delay="100">
54
+ <el-form-item
55
+ :rules="[{ required: true, message: $t('message.username'), trigger: 'blur' }]"
56
+ prop="username"
57
+ >
58
+ <el-input v-model.trim="ruleForm.username" autofocus clearable :prefix-icon="useRenderIcon(User)" />
59
+ </el-form-item>
60
+ </Motion>
61
+
62
+ <Motion :delay="150">
63
+ <el-form-item prop="passWord">
64
+ <el-input v-model="ruleForm.passWord" clearable show-password :prefix-icon="useRenderIcon(Lock)" />
65
+ </el-form-item>
66
+ </Motion>
67
+ <Motion :delay="250">
68
+ <el-form-item>
69
+ <el-button
70
+ class="w-full mt-4"
71
+ size="default"
72
+ type="primary"
73
+ :loading="loading"
74
+ @click="onLogin(ruleFormRef)"
75
+ >
76
+ {{ $t('message.udp.login') }}
77
+ </el-button>
78
+ </el-form-item>
79
+ </Motion>
80
+ </el-form>
81
+ </div>
82
+ <div class="fixed text-xs text-gray-500 bottom-4">Copyright ©2021{{ sysConfig['copyright'] }}版权所有</div>
83
+ </div>
84
+ </div>
85
+ </div>
86
+ </template>
87
+
88
+ <script setup lang="ts">
89
+ import { ref, reactive, onMounted, onBeforeMount, onBeforeUnmount } from 'vue';
90
+ import { useRouter } from 'vue-router';
91
+ import type { FormInstance } from 'element-plus';
92
+ import { storageLocal, cookies, successMessage, delay } from '@utogether/utils';
93
+ import { toDateString } from 'xe-utils';
94
+ import to from 'await-to-js';
95
+
96
+ import Motion from './utils/motion';
97
+ import { loginRules } from './utils/rule';
98
+ import TypeIt from '@/components/SuTypeit';
99
+ import { useRenderIcon } from '@/components/ReIcon/src/hooks';
100
+ // import { useTranslationLang } from '@/layout/hooks/useTranslationLang';
101
+ import { useLayout } from '@/layout/hooks/useLayout';
102
+ // import { useNav } from '@/layout/hooks/useNav';
103
+ // import { useDataThemeChange } from '@/layout/hooks/useDataThemeChange';
104
+ import { useSystemStoreHook } from '@/store/modules/system';
105
+
106
+ import { getServiceApi } from '../../api';
107
+ import { initDict } from '../../api/user';
108
+ import { getPlatform, getBrower } from '@/utils/browers';
109
+ // import dayIcon from '@/assets/svg/day.svg?component';
110
+ // import darkIcon from '@/assets/svg/dark.svg?component';
111
+ // import globalization from '@/assets/svg/globalization.svg?component';
112
+ import Lock from '@iconify-icons/ri/lock-fill';
113
+ import User from '@iconify-icons/ri/user-3-fill';
114
+
115
+ defineOptions({ name: 'LoginView' });
116
+
117
+ interface IRSAPublic {
118
+ publicKeyExponent: string;
119
+ publicKeyModulus: string;
120
+ requestKey: string;
121
+ }
122
+
123
+ const router = useRouter();
124
+
125
+ // const bgStyle = ref({});
126
+ const sysConfig = ref({});
127
+ const loading = ref(false);
128
+ const ruleFormRef = ref<FormInstance>();
129
+
130
+ const serviceApi = getServiceApi();
131
+
132
+ const { initStorage } = useLayout();
133
+ initStorage();
134
+ // const { dataTheme, dataThemeChange } = useDataThemeChange();
135
+ // dataThemeChange();
136
+ // const { getDropdownItemStyle, getDropdownItemClass } = useNav();
137
+ // const { locale, translationCh, translationEn } = useTranslationLang();
138
+
139
+ const ruleForm = reactive({
140
+ username: '',
141
+ passWord: ''
142
+ });
143
+
144
+ const publicRSA: IRSAPublic = reactive({
145
+ publicKeyExponent: '10001',
146
+ publicKeyModulus:
147
+ 'a12708ab26367e1711bd767f6bb1f29afbd85380185723d7b492230e2567c95cf5718eca745da0643400ca619fbeec892df61abe1f71ad3b822d076ed831080c53782edf8c0627ee95c57e2bee12fe55da2b3cadec59947a75ccccbbf36fb3b781c93b4bf51489789f1c0849f9023a16ec70bef41a504785e1082b6f13588e29',
148
+ requestKey: ''
149
+ });
150
+
151
+ const onLogin = async (formEl: FormInstance | undefined) => {
152
+ if (!formEl) return;
153
+ await formEl.validate(valid => {
154
+ if (valid) {
155
+ loading.value = true;
156
+ const { username, passWord } = ruleForm;
157
+
158
+ // @ts-ignore
159
+ setMaxDigits(200);
160
+ // @ts-ignore
161
+ const rsakeypair = new RSAKeyPair(publicRSA.publicKeyExponent, '', publicRSA.publicKeyModulus);
162
+ // @ts-ignore
163
+ const password = encryptedString(rsakeypair, passWord.split('').reverse().join(''));
164
+ const param = {
165
+ username,
166
+ password,
167
+ requestKey: publicRSA.requestKey,
168
+ domain: window.location.origin
169
+ };
170
+ serviceApi
171
+ .post('/uath/login', param)
172
+ .then(async (data: IResponseData) => {
173
+ successMessage(`👏 恭喜,成功登录${sysConfig.value['title']}!!!🎉`);
174
+ useSystemStoreHook().setSessionKey(data);
175
+ cacheToken(data);
176
+ cookies.set('loginer', username);
177
+ if (!storageLocal.getItem('kLov')) {
178
+ initDict().then(res => useSystemStoreHook().setDict(res));
179
+ }
180
+ await delay(300);
181
+ router.push('/');
182
+ await insertLoginInfo(username);
183
+ })
184
+ .finally(() => {
185
+ loading.value = false;
186
+ });
187
+ }
188
+ });
189
+ };
190
+
191
+ /**
192
+ * @description: 缓存token
193
+ * @param {*} token token数据
194
+ * @return {*}
195
+ */
196
+ const cacheToken = token => {
197
+ const { access_token, expires_in, refresh_token } = token;
198
+ const cache = {
199
+ accessToken: access_token,
200
+ refreshToken: refresh_token,
201
+ expires: Date.now() + expires_in * 1000
202
+ };
203
+ const kTOKENKEY = 'authorized-token';
204
+
205
+ cookies.set('kCookies_token', token.access_token);
206
+ const dataString = JSON.stringify(cache);
207
+ expires_in > 0 ? cookies.set(kTOKENKEY, dataString) : cookies.set(kTOKENKEY, dataString);
208
+ };
209
+
210
+ const insertLoginInfo = username => {
211
+ const userAgent = navigator.userAgent.toLowerCase();
212
+ const { browser, browserVersion } = getBrower(userAgent);
213
+ const obj = {
214
+ userName: username,
215
+ loginTime: toDateString(new Date()),
216
+ browser,
217
+ browserVersion,
218
+ operatingSystem: getPlatform(userAgent)
219
+ };
220
+ serviceApi.post('/upfm/v1/userMonitor', obj);
221
+ };
222
+
223
+ /** 使用公共函数,避免`removeEventListener`失效 */
224
+ function onkeypress({ code }: KeyboardEvent) {
225
+ if (['Enter', 'NumpadEnter'].includes(code)) {
226
+ onLogin(ruleFormRef.value);
227
+ }
228
+ }
229
+
230
+ onMounted(() => {
231
+ window.document.addEventListener('keypress', onkeypress);
232
+ });
233
+
234
+ onBeforeUnmount(() => {
235
+ window.document.removeEventListener('keypress', onkeypress);
236
+ });
237
+ /**
238
+ * @description: 获取系统配置
239
+ * @return {*}
240
+ */
241
+ const getSysConfig = async () => {
242
+ const [err, data]: [Error, any] = await to(serviceApi.get('/upfm/v1/sysConfig', {}));
243
+ if (!err) {
244
+ const config = {};
245
+ data.list?.forEach(item => {
246
+ config[item.configCode] = item.configValue;
247
+ if (item.fileName) {
248
+ config[item.configCode] = window.location.origin + '/ufil' + item.configValue;
249
+ }
250
+ });
251
+ const env = process.env.NODE_ENV;
252
+ const title = data.list?.find(f => f.configCode === `${env}Title` || f.configCode === 'title')?.configValue;
253
+ config['title'] = title || 'U-DP';
254
+ sysConfig.value = config;
255
+ setFavicon();
256
+ storageLocal.setItem('kSysConfig', config);
257
+ }
258
+ };
259
+
260
+ const setFavicon = () => {
261
+ let favicon = document.querySelector('link[rel="icon"]') as HTMLElement;
262
+ // console.log('app', favicon)
263
+ if (favicon !== null) {
264
+ favicon['href'] = sysConfig.value['favicon'] || '../../../public/favicon.ico';
265
+ } else {
266
+ favicon = document.createElement('link');
267
+ favicon['rel'] = 'icon';
268
+ favicon['href'] = sysConfig.value['favicon'] || '../../../public/favicon.ico';
269
+ document.head.appendChild(favicon);
270
+ }
271
+ };
272
+
273
+ onBeforeMount(() => {
274
+ getSysConfig();
275
+ });
276
+ </script>
277
+
278
+ <style scoped>
279
+ @import url('@/style/login2.css');
280
+
281
+ /* .translation {
282
+ ::v-deep(.el-dropdown-menu__item) {
283
+ padding: 5px 40px;
284
+ }
285
+ } */
286
+
287
+ .check-zh {
288
+ position: absolute;
289
+ left: 20px;
290
+ }
291
+
292
+ .check-en {
293
+ position: absolute;
294
+ left: 20px;
295
+ }
296
+
297
+ :deep(.el-input-group__append, .el-input-group__prepend) {
298
+ padding: 0;
299
+ }
300
+ </style>