vue3-admin-gpt 1.0.0

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 (118) hide show
  1. package/.env.development +14 -0
  2. package/.env.production +14 -0
  3. package/LICENSE +21 -0
  4. package/README.en.md +106 -0
  5. package/README.md +104 -0
  6. package/build-zip.cjs +53 -0
  7. package/cli.js +110 -0
  8. package/jsconfig.json +9 -0
  9. package/package.json +92 -0
  10. package/public/index.html +20 -0
  11. package/public/robots.txt +2 -0
  12. package/rspack.config.js +282 -0
  13. package/rspack.js +162 -0
  14. package/src/App.vue +9 -0
  15. package/src/api/icon.js +9 -0
  16. package/src/api/router.js +9 -0
  17. package/src/api/table.js +25 -0
  18. package/src/api/tree.js +9 -0
  19. package/src/api/user.js +34 -0
  20. package/src/assets/error_images/401.png +0 -0
  21. package/src/assets/error_images/404.png +0 -0
  22. package/src/assets/error_images/cloud.png +0 -0
  23. package/src/assets/login_images/background.jpg +0 -0
  24. package/src/assets/logo.png +0 -0
  25. package/src/assets/qr_logo/lqr_logo.png +0 -0
  26. package/src/assets/vuejs-fill.svg +4 -0
  27. package/src/components/VabPageHeader/index.vue +133 -0
  28. package/src/config/index.js +7 -0
  29. package/src/config/net.config.js +20 -0
  30. package/src/config/permission.js +136 -0
  31. package/src/config/setting.config.js +62 -0
  32. package/src/config/settings.js +6 -0
  33. package/src/config/theme.config.js +14 -0
  34. package/src/layouts/EmptyLayout.vue +3 -0
  35. package/src/layouts/components/VabAppMain/index.vue +109 -0
  36. package/src/layouts/components/VabAvatar/index.vue +255 -0
  37. package/src/layouts/components/VabBreadcrumb/index.vue +61 -0
  38. package/src/layouts/components/VabFullScreen/index.vue +61 -0
  39. package/src/layouts/components/VabLogo/index.vue +94 -0
  40. package/src/layouts/components/VabNav/index.vue +176 -0
  41. package/src/layouts/components/VabSide/components/VabMenuItem.vue +80 -0
  42. package/src/layouts/components/VabSide/components/VabSideItem.vue +100 -0
  43. package/src/layouts/components/VabSide/components/VabSubmenu.vue +56 -0
  44. package/src/layouts/components/VabSide/index.vue +123 -0
  45. package/src/layouts/components/VabTabs/index.vue +500 -0
  46. package/src/layouts/components/VabTheme/index.vue +603 -0
  47. package/src/layouts/components/VabTop/index.vue +286 -0
  48. package/src/layouts/export.js +29 -0
  49. package/src/layouts/index.vue +339 -0
  50. package/src/main.js +40 -0
  51. package/src/plugins/echarts.js +4 -0
  52. package/src/plugins/index.js +44 -0
  53. package/src/plugins/support.js +16 -0
  54. package/src/router/index.js +400 -0
  55. package/src/store/index.js +26 -0
  56. package/src/store/modules/errorLog.js +27 -0
  57. package/src/store/modules/routes.js +60 -0
  58. package/src/store/modules/settings.js +73 -0
  59. package/src/store/modules/table.js +22 -0
  60. package/src/store/modules/tabsBar.js +109 -0
  61. package/src/store/modules/user.js +131 -0
  62. package/src/styles/element-variables.scss +13 -0
  63. package/src/styles/loading.scss +345 -0
  64. package/src/styles/nav-icons.scss +52 -0
  65. package/src/styles/normalize.scss +353 -0
  66. package/src/styles/spinner/dots.css +68 -0
  67. package/src/styles/spinner/gauge.css +104 -0
  68. package/src/styles/spinner/inner-circles.css +51 -0
  69. package/src/styles/spinner/plus.css +341 -0
  70. package/src/styles/themes/default.scss +1 -0
  71. package/src/styles/transition.scss +18 -0
  72. package/src/styles/vab.scss +476 -0
  73. package/src/styles/variables.scss +69 -0
  74. package/src/utils/accessToken.js +56 -0
  75. package/src/utils/eventBus.js +8 -0
  76. package/src/utils/handleRoutes.js +100 -0
  77. package/src/utils/index.js +231 -0
  78. package/src/utils/message.js +67 -0
  79. package/src/utils/pageTitle.js +11 -0
  80. package/src/utils/password.js +43 -0
  81. package/src/utils/permission.js +19 -0
  82. package/src/utils/request.js +187 -0
  83. package/src/utils/static.js +81 -0
  84. package/src/utils/vab.js +218 -0
  85. package/src/utils/validate.js +48 -0
  86. package/src/views/401.vue +302 -0
  87. package/src/views/404.vue +302 -0
  88. package/src/views/demo/index.vue +591 -0
  89. package/src/views/index/index.vue +1489 -0
  90. package/src/views/login/index.vue +456 -0
  91. package/src/views/register/index.vue +524 -0
  92. package/src/views/vab/calendar.vue +488 -0
  93. package/src/views/vab/campaign.vue +1006 -0
  94. package/src/views/vab/chart.vue +189 -0
  95. package/src/views/vab/customer.vue +666 -0
  96. package/src/views/vab/editor.vue +84 -0
  97. package/src/views/vab/form.vue +151 -0
  98. package/src/views/vab/help.vue +390 -0
  99. package/src/views/vab/icon.vue +113 -0
  100. package/src/views/vab/knowledge.vue +820 -0
  101. package/src/views/vab/nested/menu1/menu2/menu3.vue +29 -0
  102. package/src/views/vab/nested/menu1/menu2.vue +33 -0
  103. package/src/views/vab/nested/menu1.vue +33 -0
  104. package/src/views/vab/nested.vue +97 -0
  105. package/src/views/vab/notification.vue +416 -0
  106. package/src/views/vab/order.vue +507 -0
  107. package/src/views/vab/permissions.vue +214 -0
  108. package/src/views/vab/product.vue +724 -0
  109. package/src/views/vab/project.vue +559 -0
  110. package/src/views/vab/settings.vue +319 -0
  111. package/src/views/vab/statistics.vue +431 -0
  112. package/src/views/vab/table.vue +110 -0
  113. package/src/views/vab/task.vue +613 -0
  114. package/src/views/vab/team.vue +662 -0
  115. package/src/views/vab/tree.vue +44 -0
  116. package/src/views/vab/upload.vue +180 -0
  117. package/src/views/vab/vue3Demo/index.vue +103 -0
  118. package/src/views/vab/workflow.vue +863 -0
@@ -0,0 +1,524 @@
1
+ <template>
2
+ <div class="register-container">
3
+ <div class="register-box">
4
+ <div class="register-form-container">
5
+ <div class="logo-container">
6
+ <h2 class="welcome-text">创建账号</h2>
7
+ <h3 class="system-title">加入我们的平台</h3>
8
+ </div>
9
+
10
+ <el-form
11
+ ref="registerForm"
12
+ class="register-form"
13
+ :model="form"
14
+ :rules="registerRules"
15
+ >
16
+ <el-form-item prop="username">
17
+ <el-input
18
+ v-model.trim="form.username"
19
+ v-focus
20
+ placeholder="请输入用户名"
21
+ type="text"
22
+ >
23
+ <template #prefix>
24
+ <el-icon><User /></el-icon>
25
+ </template>
26
+ </el-input>
27
+ </el-form-item>
28
+
29
+ <el-form-item prop="phone">
30
+ <el-input
31
+ v-model.trim="form.phone"
32
+ placeholder="请输入手机号"
33
+ maxlength="11"
34
+ show-word-limit
35
+ type="text"
36
+ >
37
+ <template #prefix>
38
+ <el-icon><Cellphone /></el-icon>
39
+ </template>
40
+ </el-input>
41
+ </el-form-item>
42
+
43
+ <el-form-item prop="phoneCode" class="verification-code-item">
44
+ <el-input
45
+ v-model.trim="form.phoneCode"
46
+ placeholder="手机验证码"
47
+ type="text"
48
+ >
49
+ <template #prefix>
50
+ <el-icon><Message /></el-icon>
51
+ </template>
52
+ </el-input>
53
+ <el-button
54
+ class="verification-code-btn"
55
+ :disabled="isGetphone"
56
+ type="primary"
57
+ @click="getPhoneCode"
58
+ >
59
+ {{ phoneCode }}
60
+ </el-button>
61
+ </el-form-item>
62
+
63
+ <el-form-item prop="password">
64
+ <el-input
65
+ v-model.trim="form.password"
66
+ placeholder="设置密码"
67
+ type="password"
68
+ >
69
+ <template #prefix>
70
+ <el-icon><Lock /></el-icon>
71
+ </template>
72
+ </el-input>
73
+ </el-form-item>
74
+
75
+ <div class="agreement">
76
+ <el-checkbox v-model="agreeTerms">我已阅读并同意</el-checkbox>
77
+ <a href="javascript:;" class="terms-link">服务条款和隐私政策</a>
78
+ </div>
79
+
80
+ <el-button
81
+ class="register-btn"
82
+ type="primary"
83
+ :disabled="!agreeTerms"
84
+ @click.native.prevent="handleReister"
85
+ >
86
+ 立即注册
87
+ </el-button>
88
+
89
+ <div class="login-link">
90
+ <span>已有账号?</span>
91
+ <router-link to="/login" class="back-to-login">
92
+ 返回登录
93
+ </router-link>
94
+ </div>
95
+ </el-form>
96
+ </div>
97
+
98
+ <div class="register-image">
99
+ <div class="overlay">
100
+ <h2 class="slogan">开启您的管理之旅</h2>
101
+ <p class="description">注册账号,体验全新的管理系统</p>
102
+ </div>
103
+ </div>
104
+ </div>
105
+ </div>
106
+ </template>
107
+
108
+ <script setup>
109
+ import { reactive, ref, toRefs, onUnmounted } from "vue";
110
+ import { isPassword, isPhone } from "@/utils/validate";
111
+ import { register } from "@/api/user";
112
+ import { ElMessage } from "element-plus";
113
+ import { User, Cellphone, Message, Lock } from "@element-plus/icons-vue";
114
+ import { useRouter } from "vue-router";
115
+
116
+ // 聚焦指令
117
+ const vFocus = {
118
+ mounted: (el) => el.querySelector("input").focus(),
119
+ };
120
+
121
+ // 响应式状态
122
+ const state = reactive({
123
+ form: {},
124
+ registerRules: {
125
+ username: [
126
+ { required: true, trigger: "blur", message: "请输入用户名" },
127
+ { max: 20, trigger: "blur", message: "最多不能超过20个字" },
128
+ {
129
+ validator: (rule, value, callback) => {
130
+ if (value === "") {
131
+ callback(new Error("用户名不能为空"));
132
+ } else {
133
+ callback();
134
+ }
135
+ },
136
+ trigger: "blur",
137
+ },
138
+ ],
139
+ phone: [
140
+ { required: true, trigger: "blur", message: "请输入手机号码" },
141
+ {
142
+ validator: (rule, value, callback) => {
143
+ if (!isPhone(value)) {
144
+ callback(new Error("请输入正确的手机号"));
145
+ } else {
146
+ callback();
147
+ }
148
+ },
149
+ trigger: "blur",
150
+ },
151
+ ],
152
+ password: [
153
+ { required: true, trigger: "blur", message: "请输入密码" },
154
+ {
155
+ validator: (rule, value, callback) => {
156
+ if (!isPassword(value)) {
157
+ callback(new Error("密码不能少于6位"));
158
+ } else {
159
+ callback();
160
+ }
161
+ },
162
+ trigger: "blur",
163
+ },
164
+ ],
165
+ phoneCode: [
166
+ { required: true, trigger: "blur", message: "请输入手机验证码" },
167
+ ],
168
+ },
169
+ isGetphone: false,
170
+ phoneCode: "获取验证码",
171
+ getPhoneIntval: null,
172
+ });
173
+
174
+ const registerForm = ref(null);
175
+ const agreeTerms = ref(false);
176
+ const router = useRouter();
177
+
178
+ // 获取手机验证码
179
+ const getPhoneCode = () => {
180
+ if (!isPhone(state.form.phone)) {
181
+ ElMessage.error("请输入正确的手机号");
182
+ return;
183
+ }
184
+ state.isGetphone = true;
185
+ let n = 60;
186
+ state.getPhoneIntval = setInterval(() => {
187
+ if (n > 0) {
188
+ n--;
189
+ state.phoneCode = `重新获取(${n}s)`;
190
+ } else {
191
+ clearInterval(state.getPhoneIntval);
192
+ state.getPhoneIntval = null;
193
+ state.phoneCode = "获取验证码";
194
+ state.isGetphone = false;
195
+ }
196
+ }, 1000);
197
+ };
198
+
199
+ // 处理注册
200
+ const handleReister = () => {
201
+ registerForm.value?.validate(async (valid) => {
202
+ if (valid) {
203
+ const param = {
204
+ username: state.form.username,
205
+ phone: state.form.phone,
206
+ password: state.form.password,
207
+ phoneCode: state.form.phoneCode,
208
+ };
209
+ try {
210
+ const { msg } = await register(param);
211
+ ElMessage.success(msg || "注册成功");
212
+ // 注册成功后跳转到登录页
213
+ setTimeout(() => {
214
+ router.push("/login");
215
+ }, 1500);
216
+ } catch (error) {
217
+ ElMessage.error(error.message || "注册失败");
218
+ }
219
+ }
220
+ });
221
+ };
222
+
223
+ // 在组件卸载前清除定时器
224
+ onUnmounted(() => {
225
+ if (state.getPhoneIntval) {
226
+ clearInterval(state.getPhoneIntval);
227
+ state.getPhoneIntval = null;
228
+ }
229
+ });
230
+
231
+ // 暴露响应式变量
232
+ const { form, registerRules, isGetphone, phoneCode } = toRefs(state);
233
+ </script>
234
+
235
+ <style lang="scss" scoped>
236
+ .register-container {
237
+ height: 100vh;
238
+ width: 100vw;
239
+ display: flex;
240
+ justify-content: center;
241
+ align-items: center;
242
+ background: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
243
+ }
244
+
245
+ .register-box {
246
+ width: 80%;
247
+ max-width: 1000px;
248
+ height: 700px;
249
+ border-radius: 16px;
250
+ overflow: hidden;
251
+ box-shadow: 0 10px 30px rgba(0, 0, 0, 0.1);
252
+ display: flex;
253
+ background-color: #fff;
254
+ }
255
+
256
+ .register-form-container {
257
+ width: 50%;
258
+ padding: 50px;
259
+ display: flex;
260
+ flex-direction: column;
261
+ }
262
+
263
+ .logo-container {
264
+ margin-bottom: 30px;
265
+ text-align: center;
266
+
267
+ .welcome-text {
268
+ font-size: 28px;
269
+ color: #333;
270
+ margin-bottom: 10px;
271
+ font-weight: 600;
272
+ }
273
+
274
+ .system-title {
275
+ font-size: 18px;
276
+ color: #666;
277
+ font-weight: 400;
278
+ }
279
+ }
280
+
281
+ .register-form {
282
+ flex: 1;
283
+
284
+ .el-form-item {
285
+ margin-bottom: 20px;
286
+ }
287
+
288
+ .el-input {
289
+ height: 50px;
290
+
291
+ :deep(.el-input__wrapper) {
292
+ padding-left: 15px;
293
+ box-shadow: 0 0 0 1px #dcdfe6 inset;
294
+ }
295
+
296
+ :deep(.el-input__prefix) {
297
+ color: #909399;
298
+ font-size: 18px;
299
+ }
300
+ }
301
+ }
302
+
303
+ .verification-code-item {
304
+ position: relative;
305
+
306
+ .verification-code-btn {
307
+ position: absolute;
308
+ right: 1px;
309
+ top: 5px;
310
+ width: 120px;
311
+ height: 40px;
312
+ z-index: 1;
313
+ font-size: 14px;
314
+ border-radius: 0 4px 4px 0;
315
+ }
316
+
317
+ :deep(.el-input__wrapper) {
318
+ padding-right: 130px;
319
+ }
320
+ }
321
+
322
+ .agreement {
323
+ display: flex;
324
+ align-items: center;
325
+ margin-bottom: 20px;
326
+ font-size: 14px;
327
+
328
+ .terms-link {
329
+ color: #409eff;
330
+ text-decoration: none;
331
+ margin-left: 5px;
332
+
333
+ &:hover {
334
+ text-decoration: underline;
335
+ }
336
+ }
337
+ }
338
+
339
+ .register-btn {
340
+ width: 100%;
341
+ height: 50px;
342
+ border-radius: 25px;
343
+ font-size: 16px;
344
+ font-weight: 500;
345
+ letter-spacing: 1px;
346
+ background: linear-gradient(90deg, #409eff 0%, #007aff 100%);
347
+ border: none;
348
+
349
+ &:hover {
350
+ background: linear-gradient(90deg, #007aff 0%, #409eff 100%);
351
+ }
352
+
353
+ &:disabled {
354
+ background: #a0cfff;
355
+ }
356
+ }
357
+
358
+ .login-link {
359
+ margin-top: 20px;
360
+ text-align: center;
361
+ font-size: 14px;
362
+ color: #606266;
363
+
364
+ .back-to-login {
365
+ color: #409eff;
366
+ text-decoration: none;
367
+ margin-left: 5px;
368
+
369
+ &:hover {
370
+ text-decoration: underline;
371
+ }
372
+ }
373
+ }
374
+
375
+ .register-image {
376
+ width: 50%;
377
+ position: relative;
378
+ background: url("~@/assets/login_images/background.jpg") center center
379
+ no-repeat;
380
+ background-size: cover;
381
+
382
+ .overlay {
383
+ position: absolute;
384
+ top: 0;
385
+ left: 0;
386
+ right: 0;
387
+ bottom: 0;
388
+ background: rgba(0, 0, 0, 0.4);
389
+ display: flex;
390
+ flex-direction: column;
391
+ justify-content: center;
392
+ align-items: center;
393
+ padding: 40px;
394
+
395
+ .slogan {
396
+ color: #fff;
397
+ font-size: 32px;
398
+ font-weight: 600;
399
+ margin-bottom: 20px;
400
+ text-align: center;
401
+ }
402
+
403
+ .description {
404
+ color: rgba(255, 255, 255, 0.9);
405
+ font-size: 16px;
406
+ text-align: center;
407
+ }
408
+ }
409
+ }
410
+
411
+ // 响应式设计
412
+ @media screen and (max-width: 992px) {
413
+ .register-box {
414
+ width: 100%;
415
+ max-width: 100%;
416
+ flex-direction: column;
417
+ height: auto;
418
+ max-height: 90vh;
419
+ overflow-y: auto;
420
+ }
421
+
422
+ .register-form-container,
423
+ .register-image {
424
+ width: 100%;
425
+ }
426
+
427
+ .register-image {
428
+ height: 200px;
429
+ order: -1;
430
+ }
431
+ }
432
+
433
+ @media screen and (max-width: 576px) {
434
+ .register-container {
435
+ padding: 0;
436
+ height: 100%;
437
+ background: #fff;
438
+ }
439
+
440
+ .register-box {
441
+ width: 100%;
442
+ max-width: 100%;
443
+ height: 100%;
444
+ border-radius: 0;
445
+ box-shadow: none;
446
+ }
447
+
448
+ .register-form-container {
449
+ padding: 20px;
450
+ width: 100%;
451
+ box-sizing: border-box;
452
+ }
453
+
454
+ .register-form {
455
+ .el-form-item {
456
+ margin-bottom: 15px;
457
+ width: 100%;
458
+ }
459
+
460
+ :deep(.el-input) {
461
+ width: 100%;
462
+
463
+ .el-input__wrapper {
464
+ width: 100%;
465
+ box-sizing: border-box;
466
+ }
467
+ }
468
+ }
469
+
470
+ .logo-container {
471
+ margin-bottom: 20px;
472
+
473
+ .welcome-text {
474
+ font-size: 24px;
475
+ }
476
+
477
+ .system-title {
478
+ font-size: 16px;
479
+ }
480
+ }
481
+
482
+ .verification-code-item {
483
+ .verification-code-btn {
484
+ width: 100px;
485
+ font-size: 12px;
486
+ }
487
+
488
+ :deep(.el-input__wrapper) {
489
+ padding-right: 110px;
490
+ }
491
+ }
492
+
493
+ .register-btn {
494
+ height: 45px;
495
+ font-size: 15px;
496
+ }
497
+
498
+ .agreement {
499
+ font-size: 12px;
500
+ }
501
+ }
502
+
503
+ // 添加额外的小屏幕适配
504
+ @media screen and (max-width: 375px) {
505
+ .register-form-container {
506
+ padding: 15px 10px;
507
+ }
508
+
509
+ .register-image {
510
+ height: 150px;
511
+ }
512
+
513
+ .verification-code-item {
514
+ .verification-code-btn {
515
+ width: 90px;
516
+ font-size: 11px;
517
+ }
518
+
519
+ :deep(.el-input__wrapper) {
520
+ padding-right: 100px;
521
+ }
522
+ }
523
+ }
524
+ </style>