befly-admin 3.4.6 → 3.4.8

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 (65) hide show
  1. package/.gitignore +2 -0
  2. package/index.html +2 -2
  3. package/package.json +8 -8
  4. package/src/config/{internal/index.ts → index.ts} +1 -1
  5. package/src/layouts/{internal/0.vue → default.vue} +49 -20
  6. package/src/main.ts +3 -5
  7. package/src/plugins/{internal/global.ts → global.ts} +1 -11
  8. package/src/plugins/{internal/http.ts → http.ts} +1 -1
  9. package/src/{plugins/internal/router.ts → router/index.ts} +22 -15
  10. package/src/styles/{internal/index.scss → global.scss} +29 -29
  11. package/src/types/auto-imports.d.ts +90 -645
  12. package/src/types/components.d.ts +8 -12
  13. package/src/types/typed-router.d.ts +32 -0
  14. package/src/utils/index.ts +21 -9
  15. package/src/views/index.vue +27 -0
  16. package/src/views/internal/login.vue +73 -0
  17. package/src/views/test.vue +60 -0
  18. package/tsconfig.json +4 -4
  19. package/vite.config.ts +131 -44
  20. package/src/components/internal/README.md +0 -27
  21. package/src/layouts/4.vue +0 -17
  22. package/src/layouts/internal/1.vue +0 -22
  23. package/src/layouts/internal/2.vue +0 -169
  24. package/src/layouts/internal/README.md +0 -27
  25. package/src/plugins/internal/README.md +0 -36
  26. package/src/styles/internal/README.md +0 -27
  27. package/src/styles/internal/mixins.scss +0 -98
  28. package/src/types/env.d.ts +0 -23
  29. package/src/utils/README.md +0 -37
  30. package/src/utils/internal/README.md +0 -21
  31. package/src/utils/internal/index.ts +0 -30
  32. package/src/views/internal/403/403.vue +0 -66
  33. package/src/views/internal/README.md +0 -27
  34. package/src/views/internal/admin/components/edit.vue +0 -147
  35. package/src/views/internal/admin/components/role.vue +0 -135
  36. package/src/views/internal/admin/index.vue +0 -176
  37. package/src/views/internal/dict/components/edit.vue +0 -156
  38. package/src/views/internal/dict/index.vue +0 -159
  39. package/src/views/internal/index/components/addonList.vue +0 -125
  40. package/src/views/internal/index/components/environmentInfo.vue +0 -97
  41. package/src/views/internal/index/components/operationLogs.vue +0 -112
  42. package/src/views/internal/index/components/performanceMetrics.vue +0 -148
  43. package/src/views/internal/index/components/quickActions.vue +0 -27
  44. package/src/views/internal/index/components/serviceStatus.vue +0 -181
  45. package/src/views/internal/index/components/systemNotifications.vue +0 -130
  46. package/src/views/internal/index/components/systemOverview.vue +0 -188
  47. package/src/views/internal/index/components/systemResources.vue +0 -104
  48. package/src/views/internal/index/components/userInfo.vue +0 -202
  49. package/src/views/internal/index/index.vue +0 -62
  50. package/src/views/internal/login/components/emailLoginForm.vue +0 -163
  51. package/src/views/internal/login/components/registerForm.vue +0 -168
  52. package/src/views/internal/login/components/welcomePanel.vue +0 -61
  53. package/src/views/internal/login/index_1.vue +0 -189
  54. package/src/views/internal/menu/components/edit.vue +0 -150
  55. package/src/views/internal/menu/index.vue +0 -168
  56. package/src/views/internal/news/detail/detail_2.vue +0 -26
  57. package/src/views/internal/news/detail/index.vue +0 -26
  58. package/src/views/internal/news/news.vue +0 -26
  59. package/src/views/internal/role/components/api.vue +0 -280
  60. package/src/views/internal/role/components/edit.vue +0 -129
  61. package/src/views/internal/role/components/menu.vue +0 -143
  62. package/src/views/internal/role/index.vue +0 -179
  63. package/src/views/internal/user/user.vue +0 -320
  64. /package/src/plugins/{internal/storage.ts → storage.ts} +0 -0
  65. /package/src/styles/{internal/variables.scss → variables.scss} +0 -0
@@ -1,189 +0,0 @@
1
- <template>
2
- <div class="auth-container" :class="{ 'sign-up-mode': $Data.isSignUp }">
3
- <!-- 左侧欢迎区域 -->
4
- <div class="left-panel">
5
- <WelcomePanel :is-sign-up="$Data.isSignUp" @toggle="$Method.toggleMode" />
6
- </div>
7
-
8
- <!-- 右侧表单区域 -->
9
- <div class="right-panel">
10
- <!-- 登录表单 -->
11
- <div class="form-container sign-in-form" :class="{ active: !$Data.isSignUp }">
12
- <h2 class="form-title">登录到 Befly</h2>
13
-
14
- <!-- 邮箱登录 -->
15
- <EmailLoginForm />
16
- </div>
17
-
18
- <!-- 注册表单 -->
19
- <div class="form-container sign-up-form" :class="{ active: $Data.isSignUp }">
20
- <h2 class="form-title">注册账号</h2>
21
-
22
- <RegisterForm @success="$Method.handleRegisterSuccess" />
23
- </div>
24
- </div>
25
- </div>
26
- </template>
27
-
28
- <script setup>
29
- import WelcomePanel from './components/welcomePanel.vue';
30
- import EmailLoginForm from './components/emailLoginForm.vue';
31
- import RegisterForm from './components/registerForm.vue';
32
-
33
- // 数据定义
34
- const $Data = $ref({
35
- isSignUp: false
36
- });
37
-
38
- // 方法定义
39
- const $Method = {
40
- // 切换登录/注册模式
41
- toggleMode() {
42
- $Data.isSignUp = !$Data.isSignUp;
43
- },
44
-
45
- // 注册成功后切换到登录模式
46
- handleRegisterSuccess() {
47
- $Data.isSignUp = false;
48
- }
49
- };
50
- </script>
51
-
52
- <style scoped lang="scss">
53
- .auth-container {
54
- display: flex;
55
- width: 100%;
56
- min-height: 100vh;
57
- overflow: hidden;
58
- position: relative;
59
- background: #fff;
60
- }
61
-
62
- // 青色滑动背景块
63
- .left-panel {
64
- position: absolute;
65
- top: 0;
66
- left: 0;
67
- width: 50%;
68
- height: 100%;
69
- display: flex;
70
- align-items: center;
71
- justify-content: center;
72
- background: linear-gradient(135deg, #48b19f 0%, #3a9d8f 100%);
73
- color: #fff;
74
- z-index: 5;
75
- transition: transform 0.5s ease-in-out;
76
- }
77
-
78
- // 表单区域容器(全屏背景)
79
- .right-panel {
80
- position: absolute;
81
- width: 100%;
82
- height: 100%;
83
- top: 0;
84
- left: 0;
85
- z-index: 1;
86
- }
87
-
88
- // 注册模式下青色块移动到右侧
89
- .auth-container.sign-up-mode {
90
- .left-panel {
91
- transform: translateX(100%);
92
- }
93
- }
94
-
95
- // 表单容器(跟随颜色区域滑动)
96
- .form-container {
97
- position: absolute;
98
- width: 50%;
99
- height: 100%;
100
- top: 0;
101
- display: flex;
102
- flex-direction: column;
103
- align-items: center;
104
- justify-content: center;
105
- padding: 3rem 2rem;
106
- opacity: 0;
107
- pointer-events: none;
108
- transition: all 0.5s ease-in-out;
109
-
110
- &.active {
111
- opacity: 1;
112
- pointer-events: all;
113
- }
114
- }
115
-
116
- // 登录模式:登录表单在右侧
117
- .auth-container:not(.sign-up-mode) {
118
- .sign-in-form {
119
- right: 0;
120
- }
121
-
122
- .sign-up-form {
123
- left: 0;
124
- }
125
- }
126
-
127
- // 注册模式:注册表单在左侧,登录表单在右侧
128
- .auth-container.sign-up-mode {
129
- .sign-in-form {
130
- right: -50%;
131
- }
132
-
133
- .sign-up-form {
134
- left: 0;
135
- }
136
- }
137
-
138
- .form-title {
139
- font-size: 1.8rem;
140
- color: #333;
141
- margin-bottom: 1.5rem;
142
- font-weight: 600;
143
- text-align: center;
144
- width: 100%;
145
- }
146
-
147
- // 响应式设计
148
- @media (max-width: 968px) {
149
- .auth-container {
150
- flex-direction: column;
151
- }
152
-
153
- .left-panel,
154
- .right-panel {
155
- flex: none;
156
- width: 100%;
157
- }
158
-
159
- .left-panel {
160
- order: 1 !important;
161
- position: relative;
162
- min-height: 200px;
163
- }
164
-
165
- .right-panel {
166
- order: 2 !important;
167
- min-height: 500px;
168
- }
169
-
170
- .form-container {
171
- width: 100%;
172
- padding: 2rem 1rem;
173
- position: static;
174
- }
175
-
176
- .auth-container.sign-up-mode {
177
- .left-panel {
178
- transform: none;
179
- }
180
- }
181
- }
182
-
183
- @media (max-width: 576px) {
184
- .form-title {
185
- font-size: 1.5rem;
186
- margin-bottom: 1.5rem;
187
- }
188
- }
189
- </style>
@@ -1,150 +0,0 @@
1
- <template>
2
- <tiny-dialog-box v-model:visible="$Data.visible" :title="$Prop.actionType === 'add' ? '添加菜单' : '编辑菜单'" width="600px" :append-to-body="true" :show-footer="true" top="10vh">
3
- <tiny-form :model="$Data.formData" label-width="120px" label-position="left" :rules="$Data2.formRules" :ref="(el) => ($From.form = el)">
4
- <tiny-form-item label="菜单名称" prop="name">
5
- <tiny-input v-model="$Data.formData.name" placeholder="请输入菜单名称" />
6
- </tiny-form-item>
7
- <tiny-form-item label="菜单路径" prop="path">
8
- <tiny-input v-model="$Data.formData.path" placeholder="请输入菜单路径,如:/user" />
9
- </tiny-form-item>
10
- <tiny-form-item label="图标" prop="icon">
11
- <tiny-input v-model="$Data.formData.icon" placeholder="请输入图标名称,如:User" />
12
- </tiny-form-item>
13
- <tiny-form-item label="菜单类型" prop="type">
14
- <tiny-radio-group v-model="$Data.formData.type">
15
- <tiny-radio :label="0">目录</tiny-radio>
16
- <tiny-radio :label="1">菜单</tiny-radio>
17
- </tiny-radio-group>
18
- </tiny-form-item>
19
- <tiny-form-item label="排序" prop="sort">
20
- <tiny-numeric v-model="$Data.formData.sort" :min="0" :max="9999" />
21
- </tiny-form-item>
22
- <tiny-form-item label="状态" prop="state">
23
- <tiny-radio-group v-model="$Data.formData.state">
24
- <tiny-radio :label="1">正常</tiny-radio>
25
- <tiny-radio :label="2">禁用</tiny-radio>
26
- </tiny-radio-group>
27
- </tiny-form-item>
28
- </tiny-form>
29
- <template #footer>
30
- <tiny-button @click="$Method.onClose">取消</tiny-button>
31
- <tiny-button type="primary" @click="$Method.onSubmit">确定</tiny-button>
32
- </template>
33
- </tiny-dialog-box>
34
- </template>
35
-
36
- <script setup>
37
- const $Prop = defineProps({
38
- modelValue: {
39
- type: Boolean,
40
- default: false
41
- },
42
- actionType: {
43
- type: String,
44
- default: 'add'
45
- },
46
- rowData: {
47
- type: Object,
48
- default: {}
49
- }
50
- });
51
-
52
- const $Emit = defineEmits(['update:modelValue', 'success']);
53
-
54
- // 表单引用
55
- const $From = $shallowRef({
56
- form: null
57
- });
58
-
59
- const $Data = $ref({
60
- visible: false,
61
- formData: {
62
- id: 0,
63
- name: '',
64
- path: '',
65
- icon: '',
66
- type: 1,
67
- sort: 0,
68
- state: 1
69
- }
70
- });
71
-
72
- const $Data2 = $shallowRef({
73
- formRules: {
74
- name: [{ required: true, message: '请输入菜单名称', trigger: 'blur' }],
75
- path: [{ required: true, message: '请输入菜单路径', trigger: 'blur' }],
76
- type: [{ required: true, message: '请选择菜单类型', trigger: 'change' }]
77
- }
78
- });
79
-
80
- // 方法集合
81
- const $Method = {
82
- async initData() {
83
- $Method.onShow();
84
- },
85
-
86
- onShow() {
87
- $Data.visible = true;
88
- if ($Prop.actionType === 'upd' && $Prop.rowData) {
89
- $Data.formData.id = $Prop.rowData.id || 0;
90
- $Data.formData.name = $Prop.rowData.name || '';
91
- $Data.formData.path = $Prop.rowData.path || '';
92
- $Data.formData.icon = $Prop.rowData.icon || '';
93
- $Data.formData.type = $Prop.rowData.type ?? 1;
94
- $Data.formData.sort = $Prop.rowData.sort || 0;
95
- $Data.formData.state = $Prop.rowData.state ?? 1;
96
- } else {
97
- // 重置表单
98
- $Data.formData.id = 0;
99
- $Data.formData.name = '';
100
- $Data.formData.path = '';
101
- $Data.formData.icon = '';
102
- $Data.formData.type = 1;
103
- $Data.formData.sort = 0;
104
- $Data.formData.state = 1;
105
- }
106
- },
107
-
108
- onClose() {
109
- $Data.visible = false;
110
- setTimeout(() => {
111
- $Emit('update:modelValue', false);
112
- }, 300);
113
- },
114
-
115
- async onSubmit() {
116
- try {
117
- const valid = await $From.form.validate();
118
- if (!valid) return;
119
-
120
- const res = await $Http($Prop.actionType === 'add' ? '/addon/admin/menuIns' : '/addon/admin/menuUpd', $Data.formData);
121
-
122
- Modal.message({
123
- message: $Prop.actionType === 'add' ? '添加成功' : '编辑成功',
124
- status: 'success'
125
- });
126
- $Method.onClose();
127
- $Emit('success');
128
- } catch (error) {
129
- console.error('提交失败:', error);
130
- }
131
- }
132
- };
133
-
134
- // 监听 modelValue 变化
135
- watch(
136
- () => $Prop.modelValue,
137
- (val) => {
138
- if (val && !$Data.visible) {
139
- $Method.initData();
140
- } else if (!val && $Data.visible) {
141
- $Data.visible = false;
142
- }
143
- },
144
- { immediate: true }
145
- );
146
- </script>
147
-
148
- <style scoped lang="scss">
149
- // 可根据需要添加样式
150
- </style>
@@ -1,168 +0,0 @@
1
- <template>
2
- <div class="page-menu page-table">
3
- <div class="main-tool">
4
- <div class="left">
5
- <tiny-button type="primary" @click="$Method.onAction('add', {})">
6
- <template #icon>
7
- <i-lucide:plus style="width: 16px; height: 16px" />
8
- </template>
9
- 添加菜单
10
- </tiny-button>
11
- </div>
12
- <div class="right">
13
- <tiny-button @click="$Method.handleRefresh">
14
- <template #icon>
15
- <i-lucide:rotate-cw style="width: 16px; height: 16px" />
16
- </template>
17
- 刷新
18
- </tiny-button>
19
- </div>
20
- </div>
21
- <div class="main-table">
22
- <tiny-grid :data="$Data.menuList" header-cell-class-name="custom-table-cell-class" size="small" height="100%" seq-serial>
23
- <tiny-grid-column type="index" title="序号" :width="60" />
24
- <tiny-grid-column field="name" title="菜单名称" />
25
- <tiny-grid-column field="path" title="路径" :width="200" />
26
- <tiny-grid-column field="icon" title="图标" :width="100">
27
- <template #default="{ row }">
28
- <i-lucide:square v-if="row.icon" style="width: 16px; height: 16px" />
29
- <span v-else>-</span>
30
- </template>
31
- </tiny-grid-column>
32
- <tiny-grid-column field="type" title="类型" :width="100">
33
- <template #default="{ row }">
34
- <tiny-tag v-if="row.type === 0" type="info">目录</tiny-tag>
35
- <tiny-tag v-else type="success">菜单</tiny-tag>
36
- </template>
37
- </tiny-grid-column>
38
- <tiny-grid-column field="sort" title="排序" :width="80" />
39
- <tiny-grid-column field="state" title="状态" :width="100">
40
- <template #default="{ row }">
41
- <tiny-tag v-if="row.state === 1" type="success">正常</tiny-tag>
42
- <tiny-tag v-else-if="row.state === 2" type="warning">禁用</tiny-tag>
43
- <tiny-tag v-else type="danger">已删除</tiny-tag>
44
- </template>
45
- </tiny-grid-column>
46
- <tiny-grid-column title="操作" :width="120" align="right">
47
- <template #default="{ row }">
48
- <tiny-dropdown title="操作" trigger="click" size="small" border visible-arrow @item-click="(data) => $Method.onAction(data.itemData.command, row)">
49
- <template #dropdown>
50
- <tiny-dropdown-menu>
51
- <tiny-dropdown-item :item-data="{ command: 'upd' }">
52
- <i-lucide:pencil style="width: 14px; height: 14px; margin-right: 6px" />
53
- 编辑
54
- </tiny-dropdown-item>
55
- <tiny-dropdown-item :item-data="{ command: 'del' }" divided>
56
- <i-lucide:trash-2 style="width: 14px; height: 14px; margin-right: 6px" />
57
- 删除
58
- </tiny-dropdown-item>
59
- </tiny-dropdown-menu>
60
- </template>
61
- </tiny-dropdown>
62
- </template>
63
- </tiny-grid-column>
64
- </tiny-grid>
65
- </div>
66
-
67
- <div class="main-page">
68
- <tiny-pager :current-page="$Data.pagerConfig.currentPage" :page-size="$Data.pagerConfig.pageSize" :total="$Data.pagerConfig.total" @current-change="$Method.onPageChange" @size-change="$Method.handleSizeChange" />
69
- </div>
70
-
71
- <!-- 编辑对话框组件 -->
72
- <EditDialog v-if="$Data.editVisible" v-model="$Data.editVisible" :action-type="$Data.actionType" :row-data="$Data.rowData" @success="$Method.apiMenuList" />
73
- </div>
74
- </template>
75
-
76
- <script setup>
77
- import EditDialog from './components/edit.vue';
78
-
79
- // 响应式数据
80
- const $Data = $ref({
81
- menuList: [],
82
- pagerConfig: {
83
- currentPage: 1,
84
- pageSize: 30,
85
- total: 0,
86
- align: 'right',
87
- layout: 'total, prev, pager, next, jumper'
88
- },
89
- editVisible: false,
90
- actionType: 'add',
91
- rowData: {}
92
- });
93
-
94
- // 方法
95
- const $Method = {
96
- async initData() {
97
- await $Method.apiMenuList();
98
- },
99
-
100
- // 加载菜单列表
101
- async apiMenuList() {
102
- try {
103
- const res = await $Http('/addon/admin/menu/list', {
104
- page: $Data.pagerConfig.currentPage,
105
- limit: $Data.pagerConfig.pageSize
106
- });
107
- $Data.menuList = res.data.lists || [];
108
- $Data.pagerConfig.total = res.data.total || 0;
109
- } catch (error) {
110
- console.error('加载菜单列表失败:', error);
111
- Modal.message({
112
- message: '加载数据失败',
113
- status: 'error'
114
- });
115
- }
116
- },
117
-
118
- // 删除菜单
119
- async apiMenuDel(row) {
120
- Modal.confirm({
121
- header: '确认删除',
122
- body: `确定要删除菜单"${row.name}" 吗?`,
123
- status: 'warning'
124
- }).then(async () => {
125
- try {
126
- const res = await $Http('/addon/admin/menu/del', { id: row.id });
127
- if (res.code === 0) {
128
- Modal.message({ message: '删除成功', status: 'success' });
129
- $Method.apiMenuList();
130
- } else {
131
- Modal.message({ message: res.msg || '删除失败', status: 'error' });
132
- }
133
- } catch (error) {
134
- console.error('删除失败:', error);
135
- Modal.message({ message: '删除失败', status: 'error' });
136
- }
137
- });
138
- },
139
-
140
- // 刷新
141
- handleRefresh() {
142
- $Method.apiMenuList();
143
- },
144
-
145
- // 分页改变
146
- onPageChange({ currentPage }) {
147
- $Data.pagerConfig.currentPage = currentPage;
148
- $Method.apiMenuList();
149
- },
150
-
151
- // 操作菜单点击
152
- onAction(command, rowData) {
153
- $Data.actionType = command;
154
- $Data.rowData = rowData;
155
- if (command === 'add' || command === 'upd') {
156
- $Data.editVisible = true;
157
- } else if (command === 'del') {
158
- $Method.apiMenuDel(rowData);
159
- }
160
- }
161
- };
162
-
163
- $Method.initData();
164
- </script>
165
-
166
- <style scoped lang="scss">
167
- // 样式继承自全局 page-table
168
- </style>
@@ -1,26 +0,0 @@
1
- <template>
2
- <div class="news-page">
3
- <h1>新闻页面2</h1>
4
- <p>这个页面使用布局 1.vue</p>
5
- <div class="news-content">
6
- <p>这里是新闻内容...</p>
7
- </div>
8
- </div>
9
- </template>
10
-
11
- <script setup>
12
- // 新闻页面逻辑
13
- </script>
14
-
15
- <style scoped>
16
- .news-page {
17
- padding: 20px;
18
- }
19
-
20
- .news-content {
21
- margin-top: 20px;
22
- padding: 20px;
23
- background: #f5f5f5;
24
- border-radius: 8px;
25
- }
26
- </style>
@@ -1,26 +0,0 @@
1
- <template>
2
- <div class="news-page">
3
- <h1>新闻页面 index</h1>
4
- <p>这个页面使用布局 1.vue</p>
5
- <div class="news-content">
6
- <p>这里是新闻内容...</p>
7
- </div>
8
- </div>
9
- </template>
10
-
11
- <script setup>
12
- // 新闻页面逻辑
13
- </script>
14
-
15
- <style scoped>
16
- .news-page {
17
- padding: 20px;
18
- }
19
-
20
- .news-content {
21
- margin-top: 20px;
22
- padding: 20px;
23
- background: #f5f5f5;
24
- border-radius: 8px;
25
- }
26
- </style>
@@ -1,26 +0,0 @@
1
- <template>
2
- <div class="news-page">
3
- <h1>新闻页面</h1>
4
- <p>这个页面使用布局 1.vue</p>
5
- <div class="news-content">
6
- <p>这里是新闻内容...</p>
7
- </div>
8
- </div>
9
- </template>
10
-
11
- <script setup>
12
- // 新闻页面逻辑
13
- </script>
14
-
15
- <style scoped>
16
- .news-page {
17
- padding: 20px;
18
- }
19
-
20
- .news-content {
21
- margin-top: 20px;
22
- padding: 20px;
23
- background: #f5f5f5;
24
- border-radius: 8px;
25
- }
26
- </style>