update 调整代码格式

This commit is contained in:
疯狂的狮子Li
2023-04-03 00:05:09 +08:00
parent 8b01bfd2a0
commit 1595cb282a
194 changed files with 12184 additions and 12267 deletions

View File

@ -1,281 +1,281 @@
{ {
"globals": { "globals": {
"useRouter": true, "useRouter": true,
"useRoute": true, "useRoute": true,
"EffectScope": true, "EffectScope": true,
"ElTable": true, "ElTable": true,
"ElSelect": true, "ElSelect": true,
"ElUpload": true, "ElUpload": true,
"ElForm": true, "ElForm": true,
"ElTree": true, "ElTree": true,
"ElMessage": true, "ElMessage": true,
"ElMessageBox": true, "ElMessageBox": true,
"asyncComputed": true, "asyncComputed": true,
"autoResetRef": true, "autoResetRef": true,
"computed": true, "computed": true,
"computedAsync": true, "computedAsync": true,
"computedEager": true, "computedEager": true,
"computedInject": true, "computedInject": true,
"computedWithControl": true, "computedWithControl": true,
"controlledComputed": true, "controlledComputed": true,
"controlledRef": true, "controlledRef": true,
"createApp": true, "createApp": true,
"createEventHook": true, "createEventHook": true,
"createGlobalState": true, "createGlobalState": true,
"createInjectionState": true, "createInjectionState": true,
"createReactiveFn": true, "createReactiveFn": true,
"createSharedComposable": true, "createSharedComposable": true,
"createUnrefFn": true, "createUnrefFn": true,
"customRef": true, "customRef": true,
"debouncedRef": true, "debouncedRef": true,
"debouncedWatch": true, "debouncedWatch": true,
"defineAsyncComponent": true, "defineAsyncComponent": true,
"defineComponent": true, "defineComponent": true,
"eagerComputed": true, "eagerComputed": true,
"effectScope": true, "effectScope": true,
"extendRef": true, "extendRef": true,
"getCurrentInstance": true, "getCurrentInstance": true,
"getCurrentScope": true, "getCurrentScope": true,
"h": true, "h": true,
"ignorableWatch": true, "ignorableWatch": true,
"inject": true, "inject": true,
"isDefined": true, "isDefined": true,
"isProxy": true, "isProxy": true,
"isReactive": true, "isReactive": true,
"isReadonly": true, "isReadonly": true,
"isRef": true, "isRef": true,
"makeDestructurable": true, "makeDestructurable": true,
"markRaw": true, "markRaw": true,
"nextTick": true, "nextTick": true,
"onActivated": true, "onActivated": true,
"onBeforeMount": true, "onBeforeMount": true,
"onBeforeUnmount": true, "onBeforeUnmount": true,
"onBeforeUpdate": true, "onBeforeUpdate": true,
"onClickOutside": true, "onClickOutside": true,
"onDeactivated": true, "onDeactivated": true,
"onErrorCaptured": true, "onErrorCaptured": true,
"onKeyStroke": true, "onKeyStroke": true,
"onLongPress": true, "onLongPress": true,
"onMounted": true, "onMounted": true,
"onRenderTracked": true, "onRenderTracked": true,
"onRenderTriggered": true, "onRenderTriggered": true,
"onScopeDispose": true, "onScopeDispose": true,
"onServerPrefetch": true, "onServerPrefetch": true,
"onStartTyping": true, "onStartTyping": true,
"onUnmounted": true, "onUnmounted": true,
"onUpdated": true, "onUpdated": true,
"pausableWatch": true, "pausableWatch": true,
"provide": true, "provide": true,
"reactify": true, "reactify": true,
"reactifyObject": true, "reactifyObject": true,
"reactive": true, "reactive": true,
"reactiveComputed": true, "reactiveComputed": true,
"reactiveOmit": true, "reactiveOmit": true,
"reactivePick": true, "reactivePick": true,
"readonly": true, "readonly": true,
"ref": true, "ref": true,
"refAutoReset": true, "refAutoReset": true,
"refDebounced": true, "refDebounced": true,
"refDefault": true, "refDefault": true,
"refThrottled": true, "refThrottled": true,
"refWithControl": true, "refWithControl": true,
"resolveComponent": true, "resolveComponent": true,
"resolveDirective": true, "resolveDirective": true,
"resolveRef": true, "resolveRef": true,
"resolveUnref": true, "resolveUnref": true,
"shallowReactive": true, "shallowReactive": true,
"shallowReadonly": true, "shallowReadonly": true,
"shallowRef": true, "shallowRef": true,
"syncRef": true, "syncRef": true,
"syncRefs": true, "syncRefs": true,
"templateRef": true, "templateRef": true,
"throttledRef": true, "throttledRef": true,
"throttledWatch": true, "throttledWatch": true,
"toRaw": true, "toRaw": true,
"toReactive": true, "toReactive": true,
"toRef": true, "toRef": true,
"toRefs": true, "toRefs": true,
"triggerRef": true, "triggerRef": true,
"tryOnBeforeMount": true, "tryOnBeforeMount": true,
"tryOnBeforeUnmount": true, "tryOnBeforeUnmount": true,
"tryOnMounted": true, "tryOnMounted": true,
"tryOnScopeDispose": true, "tryOnScopeDispose": true,
"tryOnUnmounted": true, "tryOnUnmounted": true,
"unref": true, "unref": true,
"unrefElement": true, "unrefElement": true,
"until": true, "until": true,
"useActiveElement": true, "useActiveElement": true,
"useArrayEvery": true, "useArrayEvery": true,
"useArrayFilter": true, "useArrayFilter": true,
"useArrayFind": true, "useArrayFind": true,
"useArrayFindIndex": true, "useArrayFindIndex": true,
"useArrayFindLast": true, "useArrayFindLast": true,
"useArrayJoin": true, "useArrayJoin": true,
"useArrayMap": true, "useArrayMap": true,
"useArrayReduce": true, "useArrayReduce": true,
"useArraySome": true, "useArraySome": true,
"useArrayUnique": true, "useArrayUnique": true,
"useAsyncQueue": true, "useAsyncQueue": true,
"useAsyncState": true, "useAsyncState": true,
"useAttrs": true, "useAttrs": true,
"useBase64": true, "useBase64": true,
"useBattery": true, "useBattery": true,
"useBluetooth": true, "useBluetooth": true,
"useBreakpoints": true, "useBreakpoints": true,
"useBroadcastChannel": true, "useBroadcastChannel": true,
"useBrowserLocation": true, "useBrowserLocation": true,
"useCached": true, "useCached": true,
"useClipboard": true, "useClipboard": true,
"useCloned": true, "useCloned": true,
"useColorMode": true, "useColorMode": true,
"useConfirmDialog": true, "useConfirmDialog": true,
"useCounter": true, "useCounter": true,
"useCssModule": true, "useCssModule": true,
"useCssVar": true, "useCssVar": true,
"useCssVars": true, "useCssVars": true,
"useCurrentElement": true, "useCurrentElement": true,
"useCycleList": true, "useCycleList": true,
"useDark": true, "useDark": true,
"useDateFormat": true, "useDateFormat": true,
"useDebounce": true, "useDebounce": true,
"useDebounceFn": true, "useDebounceFn": true,
"useDebouncedRefHistory": true, "useDebouncedRefHistory": true,
"useDeviceMotion": true, "useDeviceMotion": true,
"useDeviceOrientation": true, "useDeviceOrientation": true,
"useDevicePixelRatio": true, "useDevicePixelRatio": true,
"useDevicesList": true, "useDevicesList": true,
"useDisplayMedia": true, "useDisplayMedia": true,
"useDocumentVisibility": true, "useDocumentVisibility": true,
"useDraggable": true, "useDraggable": true,
"useDropZone": true, "useDropZone": true,
"useElementBounding": true, "useElementBounding": true,
"useElementByPoint": true, "useElementByPoint": true,
"useElementHover": true, "useElementHover": true,
"useElementSize": true, "useElementSize": true,
"useElementVisibility": true, "useElementVisibility": true,
"useEventBus": true, "useEventBus": true,
"useEventListener": true, "useEventListener": true,
"useEventSource": true, "useEventSource": true,
"useEyeDropper": true, "useEyeDropper": true,
"useFavicon": true, "useFavicon": true,
"useFetch": true, "useFetch": true,
"useFileDialog": true, "useFileDialog": true,
"useFileSystemAccess": true, "useFileSystemAccess": true,
"useFocus": true, "useFocus": true,
"useFocusWithin": true, "useFocusWithin": true,
"useFps": true, "useFps": true,
"useFullscreen": true, "useFullscreen": true,
"useGamepad": true, "useGamepad": true,
"useGeolocation": true, "useGeolocation": true,
"useIdle": true, "useIdle": true,
"useImage": true, "useImage": true,
"useInfiniteScroll": true, "useInfiniteScroll": true,
"useIntersectionObserver": true, "useIntersectionObserver": true,
"useInterval": true, "useInterval": true,
"useIntervalFn": true, "useIntervalFn": true,
"useKeyModifier": true, "useKeyModifier": true,
"useLastChanged": true, "useLastChanged": true,
"useLocalStorage": true, "useLocalStorage": true,
"useMagicKeys": true, "useMagicKeys": true,
"useManualRefHistory": true, "useManualRefHistory": true,
"useMediaControls": true, "useMediaControls": true,
"useMediaQuery": true, "useMediaQuery": true,
"useMemoize": true, "useMemoize": true,
"useMemory": true, "useMemory": true,
"useMounted": true, "useMounted": true,
"useMouse": true, "useMouse": true,
"useMouseInElement": true, "useMouseInElement": true,
"useMousePressed": true, "useMousePressed": true,
"useMutationObserver": true, "useMutationObserver": true,
"useNavigatorLanguage": true, "useNavigatorLanguage": true,
"useNetwork": true, "useNetwork": true,
"useNow": true, "useNow": true,
"useObjectUrl": true, "useObjectUrl": true,
"useOffsetPagination": true, "useOffsetPagination": true,
"useOnline": true, "useOnline": true,
"usePageLeave": true, "usePageLeave": true,
"useParallax": true, "useParallax": true,
"usePermission": true, "usePermission": true,
"usePointer": true, "usePointer": true,
"usePointerLock": true, "usePointerLock": true,
"usePointerSwipe": true, "usePointerSwipe": true,
"usePreferredColorScheme": true, "usePreferredColorScheme": true,
"usePreferredContrast": true, "usePreferredContrast": true,
"usePreferredDark": true, "usePreferredDark": true,
"usePreferredLanguages": true, "usePreferredLanguages": true,
"usePreferredReducedMotion": true, "usePreferredReducedMotion": true,
"usePrevious": true, "usePrevious": true,
"useRafFn": true, "useRafFn": true,
"useRefHistory": true, "useRefHistory": true,
"useResizeObserver": true, "useResizeObserver": true,
"useScreenOrientation": true, "useScreenOrientation": true,
"useScreenSafeArea": true, "useScreenSafeArea": true,
"useScriptTag": true, "useScriptTag": true,
"useScroll": true, "useScroll": true,
"useScrollLock": true, "useScrollLock": true,
"useSessionStorage": true, "useSessionStorage": true,
"useShare": true, "useShare": true,
"useSlots": true, "useSlots": true,
"useSorted": true, "useSorted": true,
"useSpeechRecognition": true, "useSpeechRecognition": true,
"useSpeechSynthesis": true, "useSpeechSynthesis": true,
"useStepper": true, "useStepper": true,
"useStorage": true, "useStorage": true,
"useStorageAsync": true, "useStorageAsync": true,
"useStyleTag": true, "useStyleTag": true,
"useSupported": true, "useSupported": true,
"useSwipe": true, "useSwipe": true,
"useTemplateRefsList": true, "useTemplateRefsList": true,
"useTextDirection": true, "useTextDirection": true,
"useTextSelection": true, "useTextSelection": true,
"useTextareaAutosize": true, "useTextareaAutosize": true,
"useThrottle": true, "useThrottle": true,
"useThrottleFn": true, "useThrottleFn": true,
"useThrottledRefHistory": true, "useThrottledRefHistory": true,
"useTimeAgo": true, "useTimeAgo": true,
"useTimeout": true, "useTimeout": true,
"useTimeoutFn": true, "useTimeoutFn": true,
"useTimeoutPoll": true, "useTimeoutPoll": true,
"useTimestamp": true, "useTimestamp": true,
"useTitle": true, "useTitle": true,
"useToNumber": true, "useToNumber": true,
"useToString": true, "useToString": true,
"useToggle": true, "useToggle": true,
"useTransition": true, "useTransition": true,
"useUrlSearchParams": true, "useUrlSearchParams": true,
"useUserMedia": true, "useUserMedia": true,
"useVModel": true, "useVModel": true,
"useVModels": true, "useVModels": true,
"useVibrate": true, "useVibrate": true,
"useVirtualList": true, "useVirtualList": true,
"useWakeLock": true, "useWakeLock": true,
"useWebNotification": true, "useWebNotification": true,
"useWebSocket": true, "useWebSocket": true,
"useWebWorker": true, "useWebWorker": true,
"useWebWorkerFn": true, "useWebWorkerFn": true,
"useWindowFocus": true, "useWindowFocus": true,
"useWindowScroll": true, "useWindowScroll": true,
"useWindowSize": true, "useWindowSize": true,
"watch": true, "watch": true,
"watchArray": true, "watchArray": true,
"watchAtMost": true, "watchAtMost": true,
"watchDebounced": true, "watchDebounced": true,
"watchEffect": true, "watchEffect": true,
"watchIgnorable": true, "watchIgnorable": true,
"watchOnce": true, "watchOnce": true,
"watchPausable": true, "watchPausable": true,
"watchPostEffect": true, "watchPostEffect": true,
"watchSyncEffect": true, "watchSyncEffect": true,
"watchThrottled": true, "watchThrottled": true,
"watchTriggerable": true, "watchTriggerable": true,
"watchWithFilter": true, "watchWithFilter": true,
"whenever": true, "whenever": true,
"ImportOption": true, "ImportOption": true,
"TreeType": true, "TreeType": true,
"FieldOption": true, "FieldOption": true,
"PageData": true, "PageData": true,
"storeToRefs": true, "storeToRefs": true,
"DictDataOption": true, "DictDataOption": true,
"UploadOption": true "UploadOption": true
} }
} }

View File

@ -1,41 +1,41 @@
module.exports = { module.exports = {
env: { env: {
browser: true, browser: true,
es2021: true, es2021: true,
node: true node: true
}, },
parser: 'vue-eslint-parser', parser: 'vue-eslint-parser',
extends: [ extends: [
'eslint:recommended', 'eslint:recommended',
'plugin:vue/vue3-essential', 'plugin:vue/vue3-essential',
'plugin:@typescript-eslint/recommended', 'plugin:@typescript-eslint/recommended',
'./.eslintrc-auto-import.json', './.eslintrc-auto-import.json',
'plugin:prettier/recommended' 'plugin:prettier/recommended'
], ],
parserOptions: { parserOptions: {
ecmaVersion: '2020', ecmaVersion: '2020',
sourceType: 'module', sourceType: 'module',
parser: '@typescript-eslint/parser' parser: '@typescript-eslint/parser'
}, },
plugins: ['vue', '@typescript-eslint'], plugins: ['vue', '@typescript-eslint'],
rules: { rules: {
'vue/multi-word-component-names': 'off', 'vue/multi-word-component-names': 'off',
'@typescript-eslint/no-empty-function': 'off', '@typescript-eslint/no-empty-function': 'off',
'@typescript-eslint/no-explicit-any': 'off', '@typescript-eslint/no-explicit-any': 'off',
'vue/no-v-model-argument': 'off', 'vue/no-v-model-argument': 'off',
'@typescript-eslint/ban-types': [ '@typescript-eslint/ban-types': [
'error', 'error',
{ {
// 关闭空类型检查 {} // 关闭空类型检查 {}
extendDefaults: true, extendDefaults: true,
types: { types: {
'{}': false '{}': false
} }
} }
] ]
}, },
globals: { globals: {
DialogOption: 'readonly', DialogOption: 'readonly',
OptionType: 'readonly' OptionType: 'readonly'
} }
}; };

View File

@ -2,45 +2,45 @@
* 代码格式化配置 * 代码格式化配置
*/ */
module.exports = { module.exports = {
// 一行最多多少个字符 // 一行最多多少个字符
printWidth: 150, printWidth: 150,
// 指定每个缩进级别的空格数 // 指定每个缩进级别的空格数
tabWidth: 2, tabWidth: 2,
// 使用制表符而不是空格缩进行 // 使用制表符而不是空格缩进行
useTabs: true, useTabs: false,
// 在语句末尾是否需要分号 // 在语句末尾是否需要分号
semi: true, semi: true,
// 是否使用单引号 // 是否使用单引号
singleQuote: true, singleQuote: true,
// 更改引用对象属性的时间 可选值"<as-needed|consistent|preserve>" // 更改引用对象属性的时间 可选值"<as-needed|consistent|preserve>"
quoteProps: 'as-needed', quoteProps: 'as-needed',
// 在JSX中使用单引号而不是双引号 // 在JSX中使用单引号而不是双引号
jsxSingleQuote: false, jsxSingleQuote: false,
// 多行时尽可能打印尾随逗号。(例如,单行数组永远不会出现逗号结尾。) 可选值"<none|es5|all>"默认none // 多行时尽可能打印尾随逗号。(例如,单行数组永远不会出现逗号结尾。) 可选值"<none|es5|all>"默认none
trailingComma: 'none', trailingComma: 'none',
// 在对象文字中的括号之间打印空格 // 在对象文字中的括号之间打印空格
bracketSpacing: true, bracketSpacing: true,
// jsx 标签的反尖括号需要换行 // jsx 标签的反尖括号需要换行
jsxBracketSameLine: false, jsxBracketSameLine: false,
embeddedLanguageFormatting: 'off', embeddedLanguageFormatting: 'off',
// 在单独的箭头函数参数周围包括括号 always(x) => x \ avoidx => x // 在单独的箭头函数参数周围包括括号 always(x) => x \ avoidx => x
arrowParens: 'always', arrowParens: 'always',
// 这两个选项可用于格式化以给定字符偏移量(分别包括和不包括)开始和结束的代码 // 这两个选项可用于格式化以给定字符偏移量(分别包括和不包括)开始和结束的代码
rangeStart: 0, rangeStart: 0,
rangeEnd: Infinity, rangeEnd: Infinity,
// 指定要使用的解析器,不需要写文件开头的 @prettier // 指定要使用的解析器,不需要写文件开头的 @prettier
requirePragma: false, requirePragma: false,
// 不需要自动在文件开头插入 @prettier // 不需要自动在文件开头插入 @prettier
insertPragma: false, insertPragma: false,
// 使用默认的折行标准 always\never\preserve // 使用默认的折行标准 always\never\preserve
proseWrap: 'preserve', proseWrap: 'preserve',
// 指定HTML文件的全局空格敏感度 css\strict\ignore // 指定HTML文件的全局空格敏感度 css\strict\ignore
htmlWhitespaceSensitivity: 'css', htmlWhitespaceSensitivity: 'css',
// Vue文件脚本和样式标签缩进 // Vue文件脚本和样式标签缩进
vueIndentScriptAndStyle: false, vueIndentScriptAndStyle: false,
//在 windows 操作系统中换行符通常是回车 (CR) 加换行分隔符 (LF),也就是回车换行(CRLF) //在 windows 操作系统中换行符通常是回车 (CR) 加换行分隔符 (LF),也就是回车换行(CRLF)
//然而在 Linux 和 Unix 中只使用简单的换行分隔符 (LF)。 //然而在 Linux 和 Unix 中只使用简单的换行分隔符 (LF)。
//对应的控制字符为 "\n" (LF) 和 "\r\n"(CRLF)。auto意为保持现有的行尾 //对应的控制字符为 "\n" (LF) 和 "\r\n"(CRLF)。auto意为保持现有的行尾
// 换行符使用 lf 结尾是 可选值"<auto|lf|crlf|cr>" // 换行符使用 lf 结尾是 可选值"<auto|lf|crlf|cr>"
endOfLine: 'auto' endOfLine: 'auto'
}; };

167
README.md
View File

@ -1,11 +1,9 @@
## 平台简介 ## 平台简介
## 平台简介 * 本仓库为前端技术栈 [Vue3](https://v3.cn.vuejs.org) + [TS](https://www.typescriptlang.org/) + [Element Plus](https://element-plus.org/zh-CN) + [Vite](https://cn.vitejs.dev) 版本。
* 配套后端代码仓库地址
- 本仓库为前端技术栈 [Vue3](https://v3.cn.vuejs.org) + [Element Plus](https://element-plus.org/zh-CN) + [Vite](https://cn.vitejs.dev) 版本。 * [RuoYi-Vue-Plus 5.X(注意版本号)](https://gitee.com/dromara/RuoYi-Vue-Plus)
- 配套后端代码仓库地址 * [RuoYi-Cloud-Plus 2.X(注意版本号)](https://gitee.com/dromara/RuoYi-Cloud-Plus)
- [RuoYi-Vue-Plus 5.X(注意版本号)](https://gitee.com/dromara/RuoYi-Vue-Plus)
- [RuoYi-Cloud-Plus 2.X(注意版本号)](https://gitee.com/dromara/RuoYi-Cloud-Plus)
## 前端运行 ## 前端运行
@ -19,120 +17,57 @@ npm install --registry=https://registry.npmmirror.com
# 启动服务 # 启动服务
npm run dev npm run dev
# 构建测试环境 yarn build:stage
# 构建生产环境 yarn build:prod # 构建生产环境 yarn build:prod
# 前端访问地址 http://localhost:80 # 前端访问地址 http://localhost:80
``` ```
## 本框架与 RuoYi 的业务差异 ## 本框架与RuoYi的业务差异
| 业务 | 功能说明 | 本框架 | RuoYi | | 业务 | 功能说明 | 本框架 | RuoYi |
| ------------ | --------------------------------------------------------------- | ------ | ------------------------------ | |--------|-----------------------------------------|-----|------------------|
| 租户管理 | 系统内租户的管理 如:租户套餐、过期时间、用户数量、企业信息等 | 支持 | 无 | | 租户管理 | 系统内租户的管理 如:租户套餐、过期时间、用户数量、企业信息等 | 支持 | 无 |
| 租户套餐管理 | 系统内租户所能使用的套餐管理 如:套餐内所包含的菜单等 | 支持 | 无 | | 租户套餐管理 | 系统内租户所能使用的套餐管理 如:套餐内所包含的菜单等 | 支持 | 无 |
| 用户管理 | 用户的管理配置 如:新增用户、分配用户所属部门、角色、岗位等 | 支持 | 支持 | | 用户管理 | 用户的管理配置 如:新增用户、分配用户所属部门、角色、岗位等 | 支持 | 支持 |
| 部门管理 | 配置系统组织机构(公司、部门、小组) 树结构展现支持数据权限 | 支持 | 支持 | | 部门管理 | 配置系统组织机构(公司、部门、小组) 树结构展现支持数据权限 | 支持 | 支持 |
| 岗位管理 | 配置系统用户所属担任职务 | 支持 | 支持 | | 岗位管理 | 配置系统用户所属担任职务 | 支持 | 支持 |
| 菜单管理 | 配置系统菜单、操作权限、按钮权限标识等 | 支持 | 支持 | | 菜单管理 | 配置系统菜单、操作权限、按钮权限标识等 | 支持 | 支持 |
| 角色管理 | 角色菜单权限分配、设置角色按机构进行数据范围权限划分 | 支持 | 支持 | | 角色管理 | 角色菜单权限分配、设置角色按机构进行数据范围权限划分 | 支持 | 支持 |
| 字典管理 | 对系统中经常使用的一些较为固定的数据进行维护 | 支持 | 支持 | | 字典管理 | 对系统中经常使用的一些较为固定的数据进行维护 | 支持 | 支持 |
| 参数管理 | 对系统动态配置常用参数 | 支持 | 支持 | | 参数管理 | 对系统动态配置常用参数 | 支持 | 支持 |
| 通知公告 | 系统通知公告信息发布维护 | 支持 | 支持 | | 通知公告 | 系统通知公告信息发布维护 | 支持 | 支持 |
| 操作日志 | 系统正常操作日志记录和查询 系统异常信息日志记录和查询 | 支持 | 支持 | | 操作日志 | 系统正常操作日志记录和查询 系统异常信息日志记录和查询 | 支持 | 支持 |
| 登录日志 | 系统登录日志记录查询包含登录异常 | 支持 | 支持 | | 登录日志 | 系统登录日志记录查询包含登录异常 | 支持 | 支持 |
| 文件管理 | 系统文件展示、上传、下载、删除等管理 | 支持 | 无 | | 文件管理 | 系统文件展示、上传、下载、删除等管理 | 支持 | 无 |
| 文件配置管理 | 系统文件上传、下载所需要的配置信息动态添加、修改、删除等管理 | 支持 | 无 | | 文件配置管理 | 系统文件上传、下载所需要的配置信息动态添加、修改、删除等管理 | 支持 | 无 |
| 在线用户管理 | 已登录系统的在线用户信息监控与强制踢出操作 | 支持 | 支持 | | 在线用户管理 | 已登录系统的在线用户信息监控与强制踢出操作 | 支持 | 支持 |
| 定时任务 | 运行报表、任务管理(添加、修改、删除)、日志管理、执行器管理等 | 支持 | 仅支持任务与日志管理 | | 定时任务 | 运行报表、任务管理(添加、修改、删除)、日志管理、执行器管理等 | 支持 | 仅支持任务与日志管理 |
| 代码生成 | 多数据源前后端代码的生成java、html、xml、sql支持 CRUD 下载 | 支持 | 仅支持单数据源 | | 代码生成 | 多数据源前后端代码的生成java、html、xml、sql支持CRUD下载 | 支持 | 仅支持单数据源 |
| 系统接口 | 根据业务代码自动生成相关的 api 接口文档 | 支持 | 支持 | | 系统接口 | 根据业务代码自动生成相关的api接口文档 | 支持 | 支持 |
| 服务监控 | 监视集群系统 CPU、内存、磁盘、堆栈、在线日志、Spring 相关配置等 | 支持 | 仅支持单机 CPU、内存、磁盘监控 | | 服务监控 | 监视集群系统CPU、内存、磁盘、堆栈、在线日志、Spring相关配置等 | 支持 | 仅支持单机CPU、内存、磁盘监控 |
| 缓存监控 | 对系统的缓存信息查询,命令统计等。 | 支持 | 支持 | | 缓存监控 | 对系统的缓存信息查询,命令统计等。 | 支持 | 支持 |
| 在线构建器 | 拖动表单元素生成相应的 HTML 代码。 | 支持 | 支持 | | 在线构建器 | 拖动表单元素生成相应的HTML代码。 | 支持 | 支持 |
| 使用案例 | 系统的一些功能案例 | 支持 | 不支持 | | 使用案例 | 系统的一些功能案例 | 支持 | 不支持 |
## 演示图 ## 演示图
- 本仓库为前端技术栈 [Vue3](https://v3.cn.vuejs.org) + [Element Plus](https://element-plus.org/zh-CN) + [Vite](https://cn.vitejs.dev) 版本。 | | |
- 配套后端代码仓库地址 |--------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------|
- [RuoYi-Vue-Plus 5.X(注意版本号)](https://gitee.com/dromara/RuoYi-Vue-Plus) | ![输入图片说明](https://foruda.gitee.com/images/1680077524361362822/270bb429_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680077619939771291/989bf9b6_1766278.png "屏幕截图") |
- [RuoYi-Cloud-Plus 2.X(注意版本号)](https://gitee.com/dromara/RuoYi-Cloud-Plus) | ![输入图片说明](https://foruda.gitee.com/images/1680077681751513929/1c27c5bd_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680077721559267315/74d63e23_1766278.png "屏幕截图") |
| ![输入图片说明](https://foruda.gitee.com/images/1680077765638904515/1b75d4a6_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078026375951297/eded7a4b_1766278.png "屏幕截图") |
## 前端运行 | ![输入图片说明](https://foruda.gitee.com/images/1680078237104531207/0eb1b6a7_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078254306078709/5931e22f_1766278.png "屏幕截图") |
| ![输入图片说明](https://foruda.gitee.com/images/1680078287971528493/0b9af60a_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078308138770249/8d3b6696_1766278.png "屏幕截图") |
```bash | ![输入图片说明](https://foruda.gitee.com/images/1680078352553634393/db5ef880_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078378238393374/601e4357_1766278.png "屏幕截图") |
# 克隆项目 | ![输入图片说明](https://foruda.gitee.com/images/1680078414983206024/2aae27c1_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078446738419874/ecce7d59_1766278.png "屏幕截图") |
git clone https://gitee.com/JavaLionLi/plus-ui.git | ![输入图片说明](https://foruda.gitee.com/images/1680078475971341775/149e8634_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078491666717143/3fadece7_1766278.png "屏幕截图") |
| ![输入图片说明](https://foruda.gitee.com/images/1680078558863188826/fb8ced2a_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078574561685461/ae68a0b2_1766278.png "屏幕截图") |
# 安装依赖 | ![输入图片说明](https://foruda.gitee.com/images/1680078594932772013/9d8bfec6_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078626493093532/fcfe4ff6_1766278.png "屏幕截图") |
npm install --registry=https://registry.npmmirror.com | ![输入图片说明](https://foruda.gitee.com/images/1680078643608812515/0295bd4f_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078685196286463/d7612c81_1766278.png "屏幕截图") |
| ![输入图片说明](https://foruda.gitee.com/images/1680078703877318597/56fce0bc_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078716586545643/b6dbd68f_1766278.png "屏幕截图") |
# 启动服务 | ![输入图片说明](https://foruda.gitee.com/images/1680078734103217688/eb1e6aa6_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078759131415480/73c525d8_1766278.png "屏幕截图") |
npm run dev | ![输入图片说明](https://foruda.gitee.com/images/1680078779416197879/75e3ed02_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078802329118061/77e10915_1766278.png "屏幕截图") |
| ![输入图片说明](https://foruda.gitee.com/images/1680078893627848351/34a1c342_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078928175016986/f126ec4a_1766278.png "屏幕截图") |
# 构建测试环境 yarn build:stage | ![输入图片说明](https://foruda.gitee.com/images/1680078941718318363/b68a0f72_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680078963175518631/3bb769a1_1766278.png "屏幕截图") |
# 构建生产环境 yarn build:prod | ![输入图片说明](https://foruda.gitee.com/images/1680078982294090567/b31c343d_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680079000642440444/77ca82a9_1766278.png "屏幕截图") |
# 前端访问地址 http://localhost:80 | ![输入图片说明](https://foruda.gitee.com/images/1680079020995074177/03b7d52e_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680079039367822173/76811806_1766278.png "屏幕截图") |
``` | ![输入图片说明](https://foruda.gitee.com/images/1680079274333484664/4dfdc7c0_1766278.png "屏幕截图") | ![输入图片说明](https://foruda.gitee.com/images/1680079290467458224/d6715fcf_1766278.png "屏幕截图") |
## 后端改造
参考后端代码内 `ruoyi-gen/resources/vm/vue/v3/readme.txt` 说明
## 内置功能
1. 租户管理:配置系统租户,支持 SaaS 场景下的多租户功能。
2. 用户管理:用户是系统操作者,该功能主要完成系统用户配置。
3. 部门管理:配置系统组织机构(公司、部门、小组),树结构展现支持数据权限。
4. 岗位管理:配置系统用户所属担任职务。
5. 菜单管理:配置系统菜单,操作权限,按钮权限标识等。
6. 角色管理:角色菜单权限分配、设置角色按机构进行数据范围权限划分。
7. 字典管理:对系统中经常使用的一些较为固定的数据进行维护。
8. 参数管理:对系统动态配置常用参数。
9. 通知公告:系统通知公告信息发布维护。
10. 操作日志:系统正常操作日志记录和查询;系统异常信息日志记录和查询。
11. 登录日志:系统登录日志记录查询包含登录异常。
12. 在线用户:当前系统中活跃用户状态监控。
13. 定时任务:在线(添加、修改、删除)任务调度包含执行结果日志。
14. 代码生成前后端代码的生成java、html、xml、sql支持 CRUD 下载 。
15. 系统接口:根据业务代码自动生成相关的 api 接口文档。
16. 服务监控:监视当前系统 CPU、内存、磁盘、堆栈等相关信息。
17. 缓存监控:对系统的缓存信息查询,命令统计等。
18. 在线构建器:拖动表单元素生成相应的 HTML 代码。
## 演示图
<table>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/cd1f90be5f2684f4560c9519c0f2a232ee8.jpg"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/1cbcf0e6f257c7d3a063c0e3f2ff989e4b3.jpg"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-8074972883b5ba0622e13246738ebba237a.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-9f88719cdfca9af2e58b352a20e23d43b12.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-39bf2584ec3a529b0d5a3b70d15c9b37646.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-936ec82d1f4872e1bc980927654b6007307.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-b2d62ceb95d2dd9b3fbe157bb70d26001e9.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-d67451d308b7a79ad6819723396f7c3d77a.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/5e8c387724954459291aafd5eb52b456f53.jpg"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/644e78da53c2e92a95dfda4f76e6d117c4b.jpg"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-8370a0d02977eebf6dbf854c8450293c937.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-49003ed83f60f633e7153609a53a2b644f7.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-d4fe726319ece268d4746602c39cffc0621.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-c195234bbcd30be6927f037a6755e6ab69c.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/b6115bc8c31de52951982e509930b20684a.jpg"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-5e4daac0bb59612c5038448acbcef235e3a.png"/></td>
</tr>
</table>

View File

@ -1,24 +0,0 @@
import AutoImport from 'unplugin-auto-import/vite';
import { ElementPlusResolver } from 'unplugin-vue-components/resolvers';
import IconsResolver from 'unplugin-icons/resolver';
export default (path: any) => {
return AutoImport({
// 自动导入 Vue 相关函数
imports: ['vue', 'vue-router', '@vueuse/core', 'pinia'],
eslintrc: {
enabled: false,
filepath: './.eslintrc-auto-import.json',
globalsPropValue: true
},
resolvers: [
// 自动导入 Element Plus 相关函数ElMessage, ElMessageBox... (带样式)
ElementPlusResolver(),
IconsResolver({
prefix: 'Icon'
})
],
vueTemplate: true, // 是否在 vue 模板中自动导入
dts: path.resolve(path.resolve(__dirname, '../../src'), 'types', 'auto-imports.d.ts')
});
};

View File

@ -1,17 +0,0 @@
import Components from 'unplugin-vue-components/vite';
import { ElementPlusResolver } from 'unplugin-vue-components/resolvers';
import IconsResolver from 'unplugin-icons/resolver';
export default (path: any) => {
return Components({
resolvers: [
// 自动导入 Element Plus 组件
ElementPlusResolver(),
// 自动注册图标组件
IconsResolver({
enabledCollections: ['ep']
})
],
dts: path.resolve(path.resolve(__dirname, '../../src'), 'types', 'components.d.ts')
});
};

View File

@ -1,28 +0,0 @@
import compression from 'vite-plugin-compression';
export default function createCompression(env: any) {
const { VITE_BUILD_COMPRESS } = env;
const plugin: any[] = [];
if (VITE_BUILD_COMPRESS) {
const compressList = VITE_BUILD_COMPRESS.split(',');
if (compressList.includes('gzip')) {
// http://doc.ruoyi.vip/ruoyi-vue/other/faq.html#使用gzip解压缩静态文件
plugin.push(
compression({
ext: '.gz',
deleteOriginFile: false
})
);
}
if (compressList.includes('brotli')) {
plugin.push(
compression({
ext: '.br',
algorithm: 'brotliCompress',
deleteOriginFile: false
})
);
}
}
return plugin;
}

View File

@ -1,8 +0,0 @@
import Icons from 'unplugin-icons/vite';
export default () => {
return Icons({
// 自动安装图标库
autoInstall: true
});
};

View File

@ -1,10 +0,0 @@
import { createSvgIconsPlugin } from 'vite-plugin-svg-icons';
export default (path: any, isBuild: boolean) => {
return createSvgIconsPlugin({
// 指定需要缓存的图标文件夹
iconDirs: [path.resolve(path.resolve(__dirname, '../../src'), 'assets/icons/svg')],
// 指定symbolId格式
symbolId: 'icon-[dir]-[name]',
svgoOptions: isBuild
});
};

View File

@ -1,13 +0,0 @@
import UnoCss from 'unocss/vite';
import { presetUno, presetAttributify, presetIcons } from 'unocss';
export default () => {
return UnoCss({
presets: [presetUno(), presetAttributify(), presetIcons()],
// rules: [['search', {}]],
shortcuts: {
'panel-title':
'pb-[5px] font-sans leading-[1.1] font-medium text-base text-[#6379bb] border-b border-b-solid border-[var(--el-border-color-light)] mb-5 mt-0'
}
});
};

View File

@ -1,22 +1,22 @@
module.exports = { module.exports = {
extends: ['@commitlint/config-conventional'], extends: ['@commitlint/config-conventional'],
rules: { rules: {
'type-enum': [ 'type-enum': [
2, 2,
'always', 'always',
[ [
'feat', // 新功能 feature 'feat', // 新功能 feature
'fix', // 修复 bug 'fix', // 修复 bug
'docs', // 文档注释 'docs', // 文档注释
'style', // 代码格式 'style', // 代码格式
'refactor', // 重构 'refactor', // 重构
'perf', // 性能优化 'perf', // 性能优化
'test', // 增加测试 'test', // 增加测试
'chore', // 构建过程或辅助工具的变动 'chore', // 构建过程或辅助工具的变动
'revert', // 回退 'revert', // 回退
'build' // 打包 'build' // 打包
] ]
], ],
'subject-case': [0] 'subject-case': [0]
} }
}; };

File diff suppressed because one or more lines are too long

View File

@ -1,217 +1,217 @@
<!DOCTYPE html> <!DOCTYPE html>
<html> <html>
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" /> <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="renderer" content="webkit" /> <meta name="renderer" content="webkit" />
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no" /> <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no" />
<link rel="icon" href="/favicon.ico" /> <link rel="icon" href="/favicon.ico" />
<title>RuoYi-Vue-Plus多租户管理系统</title> <title>RuoYi-Vue-Plus多租户管理系统</title>
<!--[if lt IE 11 <!--[if lt IE 11
]><script> ]><script>
window.location.href='/html/ie.html'; window.location.href='/html/ie.html';
</script><! </script><!
[endif]--> [endif]-->
<style> <style>
html, html,
body, body,
#app { #app {
height: 100%; height: 100%;
margin: 0px; margin: 0px;
padding: 0px; padding: 0px;
} }
.chromeframe { .chromeframe {
margin: 0.2em 0; margin: 0.2em 0;
background: #ccc; background: #ccc;
color: #000; color: #000;
padding: 0.2em 0; padding: 0.2em 0;
} }
#loader-wrapper { #loader-wrapper {
position: fixed; position: fixed;
top: 0; top: 0;
left: 0; left: 0;
width: 100%; width: 100%;
height: 100%; height: 100%;
z-index: 999999; z-index: 999999;
} }
#loader { #loader {
display: block; display: block;
position: relative; position: relative;
left: 50%; left: 50%;
top: 50%; top: 50%;
width: 150px; width: 150px;
height: 150px; height: 150px;
margin: -75px 0 0 -75px; margin: -75px 0 0 -75px;
border-radius: 50%; border-radius: 50%;
border: 3px solid transparent; border: 3px solid transparent;
border-top-color: #FFF; border-top-color: #FFF;
-webkit-animation: spin 2s linear infinite; -webkit-animation: spin 2s linear infinite;
-ms-animation: spin 2s linear infinite; -ms-animation: spin 2s linear infinite;
-moz-animation: spin 2s linear infinite; -moz-animation: spin 2s linear infinite;
-o-animation: spin 2s linear infinite; -o-animation: spin 2s linear infinite;
animation: spin 2s linear infinite; animation: spin 2s linear infinite;
z-index: 1001; z-index: 1001;
} }
#loader:before { #loader:before {
content: ""; content: "";
position: absolute; position: absolute;
top: 5px; top: 5px;
left: 5px; left: 5px;
right: 5px; right: 5px;
bottom: 5px; bottom: 5px;
border-radius: 50%; border-radius: 50%;
border: 3px solid transparent; border: 3px solid transparent;
border-top-color: #FFF; border-top-color: #FFF;
-webkit-animation: spin 3s linear infinite; -webkit-animation: spin 3s linear infinite;
-moz-animation: spin 3s linear infinite; -moz-animation: spin 3s linear infinite;
-o-animation: spin 3s linear infinite; -o-animation: spin 3s linear infinite;
-ms-animation: spin 3s linear infinite; -ms-animation: spin 3s linear infinite;
animation: spin 3s linear infinite; animation: spin 3s linear infinite;
} }
#loader:after { #loader:after {
content: ""; content: "";
position: absolute; position: absolute;
top: 15px; top: 15px;
left: 15px; left: 15px;
right: 15px; right: 15px;
bottom: 15px; bottom: 15px;
border-radius: 50%; border-radius: 50%;
border: 3px solid transparent; border: 3px solid transparent;
border-top-color: #FFF; border-top-color: #FFF;
-moz-animation: spin 1.5s linear infinite; -moz-animation: spin 1.5s linear infinite;
-o-animation: spin 1.5s linear infinite; -o-animation: spin 1.5s linear infinite;
-ms-animation: spin 1.5s linear infinite; -ms-animation: spin 1.5s linear infinite;
-webkit-animation: spin 1.5s linear infinite; -webkit-animation: spin 1.5s linear infinite;
animation: spin 1.5s linear infinite; animation: spin 1.5s linear infinite;
} }
@-webkit-keyframes spin { @-webkit-keyframes spin {
0% { 0% {
-webkit-transform: rotate(0deg); -webkit-transform: rotate(0deg);
-ms-transform: rotate(0deg); -ms-transform: rotate(0deg);
transform: rotate(0deg); transform: rotate(0deg);
} }
100% { 100% {
-webkit-transform: rotate(360deg); -webkit-transform: rotate(360deg);
-ms-transform: rotate(360deg); -ms-transform: rotate(360deg);
transform: rotate(360deg); transform: rotate(360deg);
} }
} }
@keyframes spin { @keyframes spin {
0% { 0% {
-webkit-transform: rotate(0deg); -webkit-transform: rotate(0deg);
-ms-transform: rotate(0deg); -ms-transform: rotate(0deg);
transform: rotate(0deg); transform: rotate(0deg);
} }
100% { 100% {
-webkit-transform: rotate(360deg); -webkit-transform: rotate(360deg);
-ms-transform: rotate(360deg); -ms-transform: rotate(360deg);
transform: rotate(360deg); transform: rotate(360deg);
} }
} }
#loader-wrapper .loader-section { #loader-wrapper .loader-section {
position: fixed; position: fixed;
top: 0; top: 0;
width: 51%; width: 51%;
height: 100%; height: 100%;
background: #7171C6; background: #7171C6;
z-index: 1000; z-index: 1000;
-webkit-transform: translateX(0); -webkit-transform: translateX(0);
-ms-transform: translateX(0); -ms-transform: translateX(0);
transform: translateX(0); transform: translateX(0);
} }
#loader-wrapper .loader-section.section-left { #loader-wrapper .loader-section.section-left {
left: 0; left: 0;
} }
#loader-wrapper .loader-section.section-right { #loader-wrapper .loader-section.section-right {
right: 0; right: 0;
} }
.loaded #loader-wrapper .loader-section.section-left { .loaded #loader-wrapper .loader-section.section-left {
-webkit-transform: translateX(-100%); -webkit-transform: translateX(-100%);
-ms-transform: translateX(-100%); -ms-transform: translateX(-100%);
transform: translateX(-100%); transform: translateX(-100%);
-webkit-transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000); -webkit-transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000);
transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000); transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000);
} }
.loaded #loader-wrapper .loader-section.section-right { .loaded #loader-wrapper .loader-section.section-right {
-webkit-transform: translateX(100%); -webkit-transform: translateX(100%);
-ms-transform: translateX(100%); -ms-transform: translateX(100%);
transform: translateX(100%); transform: translateX(100%);
-webkit-transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000); -webkit-transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000);
transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000); transition: all 0.7s 0.3s cubic-bezier(0.645, 0.045, 0.355, 1.000);
} }
.loaded #loader { .loaded #loader {
opacity: 0; opacity: 0;
-webkit-transition: all 0.3s ease-out; -webkit-transition: all 0.3s ease-out;
transition: all 0.3s ease-out; transition: all 0.3s ease-out;
} }
.loaded #loader-wrapper { .loaded #loader-wrapper {
visibility: hidden; visibility: hidden;
-webkit-transform: translateY(-100%); -webkit-transform: translateY(-100%);
-ms-transform: translateY(-100%); -ms-transform: translateY(-100%);
transform: translateY(-100%); transform: translateY(-100%);
-webkit-transition: all 0.3s 1s ease-out; -webkit-transition: all 0.3s 1s ease-out;
transition: all 0.3s 1s ease-out; transition: all 0.3s 1s ease-out;
} }
.no-js #loader-wrapper { .no-js #loader-wrapper {
display: none; display: none;
} }
.no-js h1 { .no-js h1 {
color: #222222; color: #222222;
} }
#loader-wrapper .load_title { #loader-wrapper .load_title {
font-family: 'Open Sans'; font-family: 'Open Sans';
color: #FFF; color: #FFF;
font-size: 19px; font-size: 19px;
width: 100%; width: 100%;
text-align: center; text-align: center;
z-index: 9999999999999; z-index: 9999999999999;
position: absolute; position: absolute;
top: 60%; top: 60%;
opacity: 1; opacity: 1;
line-height: 30px; line-height: 30px;
} }
#loader-wrapper .load_title span { #loader-wrapper .load_title span {
font-weight: normal; font-weight: normal;
font-style: italic; font-style: italic;
font-size: 13px; font-size: 13px;
color: #FFF; color: #FFF;
opacity: 0.5; opacity: 0.5;
} }
</style> </style>
</head> </head>
<body> <body>
<div id="app"> <div id="app">
<div id="loader-wrapper"> <div id="loader-wrapper">
<div id="loader"></div> <div id="loader"></div>
<div class="loader-section section-left"></div> <div class="loader-section section-left"></div>
<div class="loader-section section-right"></div> <div class="loader-section section-right"></div>
<div class="load_title">正在加载系统资源,请耐心等待</div> <div class="load_title">正在加载系统资源,请耐心等待</div>
</div> </div>
</div> </div>
<script type="module" src="/src/main.ts"></script> <script type="module" src="/src/main.ts"></script>
</body> </body>
</html> </html>

View File

@ -1,80 +1,80 @@
{ {
"name": "ruoyi-vue-plus", "name": "ruoyi-vue-plus",
"version": "5.0.0-SNAPSHOT", "version": "5.0.0-SNAPSHOT",
"description": "RuoYi-Vue-Plus多租户管理系统", "description": "RuoYi-Vue-Plus多租户管理系统",
"author": "LionLi", "author": "LionLi",
"license": "MIT", "license": "MIT",
"scripts": { "scripts": {
"dev": "vite serve --mode development", "dev": "vite serve --mode development",
"build:prod": "vite build --mode production &&vue-tsc --noEmit", "build:prod": "vite build --mode production &&vue-tsc --noEmit",
"preview": "vite preview", "preview": "vite preview",
"lint": "eslint src/**/*.{ts,js,vue} --fix", "lint": "eslint src/**/*.{ts,js,vue} --fix",
"prepare": "husky install", "prepare": "husky install",
"prettier": "prettier --write ." "prettier": "prettier --write ."
}, },
"repository": { "repository": {
"type": "git", "type": "git",
"url": "https://gitee.com/JavaLionLi/plus-ui.git" "url": "https://gitee.com/JavaLionLi/plus-ui.git"
}, },
"dependencies": { "dependencies": {
"@element-plus/icons-vue": "2.1.0", "@element-plus/icons-vue": "2.1.0",
"@vueup/vue-quill": "1.1.0", "@vueup/vue-quill": "1.1.0",
"@vueuse/core": "9.5.0", "@vueuse/core": "9.5.0",
"animate.css": "4.1.1", "animate.css": "4.1.1",
"await-to-js": "^3.0.0", "await-to-js": "^3.0.0",
"axios": "^1.3.4", "axios": "^1.3.4",
"echarts": "5.4.0", "echarts": "5.4.0",
"element-plus": "2.2.27", "element-plus": "2.2.27",
"file-saver": "2.0.5", "file-saver": "2.0.5",
"fuse.js": "6.6.2", "fuse.js": "6.6.2",
"js-cookie": "3.0.1", "js-cookie": "3.0.1",
"jsencrypt": "3.3.1", "jsencrypt": "3.3.1",
"nprogress": "0.2.0", "nprogress": "0.2.0",
"path-browserify": "1.0.1", "path-browserify": "1.0.1",
"path-to-regexp": "6.2.0", "path-to-regexp": "6.2.0",
"pinia": "2.0.22", "pinia": "2.0.22",
"screenfull": "6.0.0", "screenfull": "6.0.0",
"vue": "3.2.45", "vue": "3.2.45",
"vue-cropper": "1.0.3", "vue-cropper": "1.0.3",
"vue-i18n": "9.2.2", "vue-i18n": "9.2.2",
"vue-router": "4.1.4" "vue-router": "4.1.4"
}, },
"devDependencies": { "devDependencies": {
"@iconify/json": "^2.2.40", "@iconify/json": "^2.2.40",
"@intlify/unplugin-vue-i18n": "0.8.2", "@intlify/unplugin-vue-i18n": "0.8.2",
"@types/file-saver": "2.0.5", "@types/file-saver": "2.0.5",
"@types/js-cookie": "3.0.3", "@types/js-cookie": "3.0.3",
"@types/node": "18.14.2", "@types/node": "18.14.2",
"@types/nprogress": "0.2.0", "@types/nprogress": "0.2.0",
"@types/path-browserify": "^1.0.0", "@types/path-browserify": "^1.0.0",
"@typescript-eslint/eslint-plugin": "5.56.0", "@typescript-eslint/eslint-plugin": "5.56.0",
"@typescript-eslint/parser": "5.56.0", "@typescript-eslint/parser": "5.56.0",
"@unocss/preset-attributify": "^0.50.6", "@unocss/preset-attributify": "^0.50.6",
"@unocss/preset-icons": "^0.50.6", "@unocss/preset-icons": "^0.50.6",
"@unocss/preset-uno": "^0.50.6", "@unocss/preset-uno": "^0.50.6",
"@vitejs/plugin-vue": "4.0.0", "@vitejs/plugin-vue": "4.0.0",
"@vue/compiler-sfc": "3.2.45", "@vue/compiler-sfc": "3.2.45",
"autoprefixer": "10.4.14", "autoprefixer": "10.4.14",
"eslint": "8.36.0", "eslint": "8.36.0",
"eslint-config-prettier": "8.8.0", "eslint-config-prettier": "8.8.0",
"eslint-plugin-prettier": "4.2.1", "eslint-plugin-prettier": "4.2.1",
"eslint-plugin-vue": "9.9.0", "eslint-plugin-vue": "9.9.0",
"fast-glob": "^3.2.11", "fast-glob": "^3.2.11",
"husky": "7.0.4", "husky": "7.0.4",
"postcss": "^8.4.21", "postcss": "^8.4.21",
"prettier": "2.8.6", "prettier": "2.8.6",
"sass": "1.56.1", "sass": "1.56.1",
"typescript": "4.9.5", "typescript": "4.9.5",
"unocss": "^0.50.6", "unocss": "^0.50.6",
"unplugin-auto-import": "0.13.0", "unplugin-auto-import": "0.13.0",
"unplugin-icons": "0.15.1", "unplugin-icons": "0.15.1",
"unplugin-vue-components": "0.23.0", "unplugin-vue-components": "0.23.0",
"vite": "4.1.4", "vite": "4.1.4",
"vite-plugin-compression": "0.5.1", "vite-plugin-compression": "0.5.1",
"vite-plugin-svg-icons": "2.0.1", "vite-plugin-svg-icons": "2.0.1",
"vite-plugin-vue-setup-extend": "0.4.0", "vite-plugin-vue-setup-extend": "0.4.0",
"vitest": "^0.29.7", "vitest": "^0.29.7",
"vue-eslint-parser": "9.1.0", "vue-eslint-parser": "9.1.0",
"vue-tsc": "0.35.0" "vue-tsc": "0.35.0"
} }
} }

View File

@ -1,7 +1,7 @@
<template> <template>
<el-config-provider :locale="appStore.locale" :size="size"> <el-config-provider :locale="appStore.locale" :size="size">
<router-view /> <router-view />
</el-config-provider> </el-config-provider>
</template> </template>
<script setup lang="ts"> <script setup lang="ts">

View File

@ -2,47 +2,47 @@
const animatePrefix = 'animate__animated '; const animatePrefix = 'animate__animated ';
// 开启随机动画 随机动画值 // 开启随机动画 随机动画值
const animateList: string[] = [ const animateList: string[] = [
animatePrefix + 'animate__pulse', animatePrefix + 'animate__pulse',
animatePrefix + 'animate__rubberBand', animatePrefix + 'animate__rubberBand',
animatePrefix + 'animate__bounceIn', animatePrefix + 'animate__bounceIn',
animatePrefix + 'animate__bounceInLeft', animatePrefix + 'animate__bounceInLeft',
animatePrefix + 'animate__fadeIn', animatePrefix + 'animate__fadeIn',
animatePrefix + 'animate__fadeInLeft', animatePrefix + 'animate__fadeInLeft',
animatePrefix + 'animate__fadeInDown', animatePrefix + 'animate__fadeInDown',
animatePrefix + 'animate__fadeInUp', animatePrefix + 'animate__fadeInUp',
animatePrefix + 'animate__flipInX', animatePrefix + 'animate__flipInX',
animatePrefix + 'animate__lightSpeedInLeft', animatePrefix + 'animate__lightSpeedInLeft',
animatePrefix + 'animate__rotateInDownLeft', animatePrefix + 'animate__rotateInDownLeft',
animatePrefix + 'animate__rollIn', animatePrefix + 'animate__rollIn',
animatePrefix + 'animate__rotateInDownLeft', animatePrefix + 'animate__rotateInDownLeft',
animatePrefix + 'animate__zoomIn', animatePrefix + 'animate__zoomIn',
animatePrefix + 'animate__zoomInDown', animatePrefix + 'animate__zoomInDown',
animatePrefix + 'animate__slideInLeft', animatePrefix + 'animate__slideInLeft',
animatePrefix + 'animate__lightSpeedIn' animatePrefix + 'animate__lightSpeedIn'
]; ];
// 关闭随机动画后的默认效果 // 关闭随机动画后的默认效果
const defaultAnimate = animatePrefix + 'animate__fadeIn'; const defaultAnimate = animatePrefix + 'animate__fadeIn';
// 搜索隐藏显示动画 // 搜索隐藏显示动画
const searchAnimate = { const searchAnimate = {
enter: '', enter: '',
leave: '' leave: ''
}; };
// 菜单搜索动画 // 菜单搜索动画
const menuSearchAnimate = { const menuSearchAnimate = {
enter: animatePrefix + 'animate__fadeIn', enter: animatePrefix + 'animate__fadeIn',
leave: animatePrefix + 'animate__fadeOut' leave: animatePrefix + 'animate__fadeOut'
}; };
// logo动画 // logo动画
const logoAnimate = { const logoAnimate = {
enter: animatePrefix + 'animate__fadeIn', enter: animatePrefix + 'animate__fadeIn',
leave: animatePrefix + 'animate__fadeOut' leave: animatePrefix + 'animate__fadeOut'
}; };
export default { export default {
animateList, animateList,
defaultAnimate, defaultAnimate,
searchAnimate, searchAnimate,
menuSearchAnimate, menuSearchAnimate,
logoAnimate logoAnimate
}; };

View File

@ -4,52 +4,52 @@ import { AxiosPromise } from 'axios';
// 查询测试单表列表 // 查询测试单表列表
export function listDemo(query: DemoQuery): AxiosPromise<DemoVO[]> { export function listDemo(query: DemoQuery): AxiosPromise<DemoVO[]> {
return request({ return request({
url: '/demo/demo/list', url: '/demo/demo/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 自定义分页接口 // 自定义分页接口
export function pageDemo(query: DemoQuery): AxiosPromise<DemoVO[]> { export function pageDemo(query: DemoQuery): AxiosPromise<DemoVO[]> {
return request({ return request({
url: '/demo/demo/page', url: '/demo/demo/page',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询测试单表详细 // 查询测试单表详细
export function getDemo(id: string | number): AxiosPromise<DemoVO> { export function getDemo(id: string | number): AxiosPromise<DemoVO> {
return request({ return request({
url: '/demo/demo/' + id, url: '/demo/demo/' + id,
method: 'get' method: 'get'
}); });
} }
// 新增测试单表 // 新增测试单表
export function addDemo(data: DemoForm) { export function addDemo(data: DemoForm) {
return request({ return request({
url: '/demo/demo', url: '/demo/demo',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改测试单表 // 修改测试单表
export function updateDemo(data: DemoForm) { export function updateDemo(data: DemoForm) {
return request({ return request({
url: '/demo/demo', url: '/demo/demo',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除测试单表 // 删除测试单表
export function delDemo(id: string | number | Array<string | number>) { export function delDemo(id: string | number | Array<string | number>) {
return request({ return request({
url: '/demo/demo/' + id, url: '/demo/demo/' + id,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -4,43 +4,43 @@ import { DemoTreeForm, DemoTreeVO, DemoTreeQuery } from './types';
// 查询测试树表列表 // 查询测试树表列表
export function listTree(query?: DemoTreeQuery): AxiosPromise<DemoTreeVO[]> { export function listTree(query?: DemoTreeQuery): AxiosPromise<DemoTreeVO[]> {
return request({ return request({
url: '/demo/tree/list', url: '/demo/tree/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询测试树表详细 // 查询测试树表详细
export function getTree(id: string | number): AxiosPromise<DemoTreeVO> { export function getTree(id: string | number): AxiosPromise<DemoTreeVO> {
return request({ return request({
url: '/demo/tree/' + id, url: '/demo/tree/' + id,
method: 'get' method: 'get'
}); });
} }
// 新增测试树表 // 新增测试树表
export function addTree(data: DemoTreeForm) { export function addTree(data: DemoTreeForm) {
return request({ return request({
url: '/demo/tree', url: '/demo/tree',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改测试树表 // 修改测试树表
export function updateTree(data: DemoTreeForm) { export function updateTree(data: DemoTreeForm) {
return request({ return request({
url: '/demo/tree', url: '/demo/tree',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除测试树表 // 删除测试树表
export function delTree(id: string | number | Array<string | number>) { export function delTree(id: string | number | Array<string | number>) {
return request({ return request({
url: '/demo/tree/' + id, url: '/demo/tree/' + id,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,55 +1,55 @@
export interface DemoVO extends BaseEntity { export interface DemoVO extends BaseEntity {
id: number | string; id: number | string;
deptId: number | string; deptId: number | string;
userId: number | string; userId: number | string;
orderNum: number; orderNum: number;
testKey: string; testKey: string;
value: string; value: string;
createByName: string; createByName: string;
updateByName?: any; updateByName?: any;
} }
export interface DemoQuery extends PageQuery { export interface DemoQuery extends PageQuery {
testKey: string; testKey: string;
value: string; value: string;
createTime: string; createTime: string;
} }
export interface DemoForm { export interface DemoForm {
id: string | number | undefined; id: string | number | undefined;
deptId: string | number | undefined; deptId: string | number | undefined;
userId: string | number | undefined; userId: string | number | undefined;
orderNum: number; orderNum: number;
testKey: string; testKey: string;
value: string; value: string;
version: string; version: string;
ossConfigId: string | number | undefined; ossConfigId: string | number | undefined;
createTime?: string; createTime?: string;
} }
export interface DemoTreeVO extends BaseEntity { export interface DemoTreeVO extends BaseEntity {
id: number | string; id: number | string;
parentId: number | string; parentId: number | string;
deptId: number | string; deptId: number | string;
userId: number | string; userId: number | string;
treeName: string; treeName: string;
children?: DemoTreeVO[]; children?: DemoTreeVO[];
} }
export interface DemoTreeQuery { export interface DemoTreeQuery {
treeName: string; treeName: string;
createTime: string; createTime: string;
} }
export interface DemoTreeForm { export interface DemoTreeForm {
id: string | number | undefined; id: string | number | undefined;
parentId: string | number | undefined; parentId: string | number | undefined;
deptId: string | number | undefined; deptId: string | number | undefined;
userId: string | number | undefined; userId: string | number | undefined;
treeName: string; treeName: string;
} }
export interface DemoTreeOptionsType { export interface DemoTreeOptionsType {
id: string | number; id: string | number;
treeName: string; treeName: string;
children?: DemoTreeOptionsType[]; children?: DemoTreeOptionsType[];
} }

View File

@ -8,74 +8,74 @@ import { UserInfo } from '@/api/system/user/types';
* @returns * @returns
*/ */
export function login(data: LoginData): AxiosPromise<LoginResult> { export function login(data: LoginData): AxiosPromise<LoginResult> {
const params = { const params = {
tenantId: data.tenantId, tenantId: data.tenantId,
username: data.username.trim(), username: data.username.trim(),
password: data.password, password: data.password,
code: data.code, code: data.code,
uuid: data.uuid uuid: data.uuid
}; };
return request({ return request({
url: '/auth/login', url: '/auth/login',
headers: { headers: {
isToken: false isToken: false
}, },
method: 'post', method: 'post',
data: params data: params
}); });
} }
// 注册方法 // 注册方法
export function register(data: any) { export function register(data: any) {
return request({ return request({
url: '/auth/register', url: '/auth/register',
headers: { headers: {
isToken: false isToken: false
}, },
method: 'post', method: 'post',
data: data data: data
}); });
} }
/** /**
* 注销 * 注销
*/ */
export function logout() { export function logout() {
return request({ return request({
url: '/auth/logout', url: '/auth/logout',
method: 'post' method: 'post'
}); });
} }
/** /**
* 获取验证码 * 获取验证码
*/ */
export function getCodeImg(): AxiosPromise<VerifyCodeResult> { export function getCodeImg(): AxiosPromise<VerifyCodeResult> {
return request({ return request({
url: '/code', url: '/code',
headers: { headers: {
isToken: false isToken: false
}, },
method: 'get', method: 'get',
timeout: 20000 timeout: 20000
}); });
} }
// 获取用户详细信息 // 获取用户详细信息
export function getInfo(): AxiosPromise<UserInfo> { export function getInfo(): AxiosPromise<UserInfo> {
return request({ return request({
url: '/system/user/getInfo', url: '/system/user/getInfo',
method: 'get' method: 'get'
}); });
} }
// 获取租户列表 // 获取租户列表
export function getTenantList(): AxiosPromise<TenantInfo> { export function getTenantList(): AxiosPromise<TenantInfo> {
return request({ return request({
url: '/auth/tenant/list', url: '/auth/tenant/list',
headers: { headers: {
isToken: false isToken: false
}, },
method: 'get' method: 'get'
}); });
} }

View File

@ -4,8 +4,8 @@ import { RouteRecordRaw } from 'vue-router';
// 获取路由 // 获取路由
export function getRouters(): AxiosPromise<RouteRecordRaw[]> { export function getRouters(): AxiosPromise<RouteRecordRaw[]> {
return request({ return request({
url: '/system/menu/getRouters', url: '/system/menu/getRouters',
method: 'get' method: 'get'
}); });
} }

View File

@ -4,56 +4,56 @@ import { CacheVO } from './types';
// 查询缓存详细 // 查询缓存详细
export function getCache(): AxiosPromise<CacheVO> { export function getCache(): AxiosPromise<CacheVO> {
return request({ return request({
url: '/monitor/cache', url: '/monitor/cache',
method: 'get' method: 'get'
}); });
} }
// 查询缓存名称列表 // 查询缓存名称列表
export function listCacheName() { export function listCacheName() {
return request({ return request({
url: '/monitor/cache/getNames', url: '/monitor/cache/getNames',
method: 'get' method: 'get'
}); });
} }
// 查询缓存键名列表 // 查询缓存键名列表
export function listCacheKey(cacheName: string) { export function listCacheKey(cacheName: string) {
return request({ return request({
url: '/monitor/cache/getKeys/' + cacheName, url: '/monitor/cache/getKeys/' + cacheName,
method: 'get' method: 'get'
}); });
} }
// 查询缓存内容 // 查询缓存内容
export function getCacheValue(cacheName: string, cacheKey: string) { export function getCacheValue(cacheName: string, cacheKey: string) {
return request({ return request({
url: '/monitor/cache/getValue/' + cacheName + '/' + cacheKey, url: '/monitor/cache/getValue/' + cacheName + '/' + cacheKey,
method: 'get' method: 'get'
}); });
} }
// 清理指定名称缓存 // 清理指定名称缓存
export function clearCacheName(cacheName: string) { export function clearCacheName(cacheName: string) {
return request({ return request({
url: '/monitor/cache/clearCacheName/' + cacheName, url: '/monitor/cache/clearCacheName/' + cacheName,
method: 'delete' method: 'delete'
}); });
} }
// 清理指定键名缓存 // 清理指定键名缓存
export function clearCacheKey(cacheName: string, cacheKey: string) { export function clearCacheKey(cacheName: string, cacheKey: string) {
return request({ return request({
url: '/monitor/cache/clearCacheKey/' + cacheName + '/' + cacheKey, url: '/monitor/cache/clearCacheKey/' + cacheName + '/' + cacheKey,
method: 'delete' method: 'delete'
}); });
} }
// 清理全部缓存 // 清理全部缓存
export function clearCacheAll() { export function clearCacheAll() {
return request({ return request({
url: '/monitor/cache/clearCacheAll', url: '/monitor/cache/clearCacheAll',
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,7 +1,7 @@
export interface CacheVO { export interface CacheVO {
commandStats: Array<{ name: string; value: string }>; commandStats: Array<{ name: string; value: string }>;
dbSize: number; dbSize: number;
info: { [key: string]: string }; info: { [key: string]: string };
} }

View File

@ -4,33 +4,33 @@ import { AxiosPromise } from 'axios';
// 查询登录日志列表 // 查询登录日志列表
export function list(query: LoginInfoQuery): AxiosPromise<LoginInfoVO[]> { export function list(query: LoginInfoQuery): AxiosPromise<LoginInfoVO[]> {
return request({ return request({
url: '/monitor/logininfor/list', url: '/monitor/logininfor/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 删除登录日志 // 删除登录日志
export function delLoginInfo(infoId: string | number | Array<string | number>) { export function delLoginInfo(infoId: string | number | Array<string | number>) {
return request({ return request({
url: '/monitor/logininfor/' + infoId, url: '/monitor/logininfor/' + infoId,
method: 'delete' method: 'delete'
}); });
} }
// 解锁用户登录状态 // 解锁用户登录状态
export function unlockLoginInfo(userName: string | Array<string>) { export function unlockLoginInfo(userName: string | Array<string>) {
return request({ return request({
url: '/monitor/logininfor/unlock/' + userName, url: '/monitor/logininfor/unlock/' + userName,
method: 'get' method: 'get'
}); });
} }
// 清空登录日志 // 清空登录日志
export function cleanLoginInfo() { export function cleanLoginInfo() {
return request({ return request({
url: '/monitor/logininfor/clean', url: '/monitor/logininfor/clean',
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,20 +1,20 @@
export interface LoginInfoVO { export interface LoginInfoVO {
infoId: string | number; infoId: string | number;
tenantId: string | number; tenantId: string | number;
userName: string; userName: string;
status: string; status: string;
ipaddr: string; ipaddr: string;
loginLocation: string; loginLocation: string;
browser: string; browser: string;
os: string; os: string;
msg: string; msg: string;
loginTime: string; loginTime: string;
} }
export interface LoginInfoQuery extends PageQuery { export interface LoginInfoQuery extends PageQuery {
ipaddr: string; ipaddr: string;
userName: string; userName: string;
status: string; status: string;
orderByColumn: string; orderByColumn: string;
isAsc: string; isAsc: string;
} }

View File

@ -4,17 +4,17 @@ import { AxiosPromise } from 'axios';
// 查询在线用户列表 // 查询在线用户列表
export function list(query: OnlineQuery): AxiosPromise<OnlineVO[]> { export function list(query: OnlineQuery): AxiosPromise<OnlineVO[]> {
return request({ return request({
url: '/monitor/online/list', url: '/monitor/online/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 强退用户 // 强退用户
export function forceLogout(tokenId: string) { export function forceLogout(tokenId: string) {
return request({ return request({
url: '/monitor/online/' + tokenId, url: '/monitor/online/' + tokenId,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,15 +1,15 @@
export interface OnlineQuery extends PageQuery { export interface OnlineQuery extends PageQuery {
ipaddr: string; ipaddr: string;
userName: string; userName: string;
} }
export interface OnlineVO extends BaseEntity { export interface OnlineVO extends BaseEntity {
tokenId: string; tokenId: string;
deptName: string; deptName: string;
userName: string; userName: string;
ipaddr: string; ipaddr: string;
loginLocation: string; loginLocation: string;
browser: string; browser: string;
os: string; os: string;
loginTime: number; loginTime: number;
} }

View File

@ -4,25 +4,25 @@ import { AxiosPromise } from 'axios';
// 查询操作日志列表 // 查询操作日志列表
export function list(query: OperLogQuery): AxiosPromise<OperLogVO[]> { export function list(query: OperLogQuery): AxiosPromise<OperLogVO[]> {
return request({ return request({
url: '/monitor/operlog/list', url: '/monitor/operlog/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 删除操作日志 // 删除操作日志
export function delOperlog(operId: string | number | Array<string | number>) { export function delOperlog(operId: string | number | Array<string | number>) {
return request({ return request({
url: '/monitor/operlog/' + operId, url: '/monitor/operlog/' + operId,
method: 'delete' method: 'delete'
}); });
} }
// 清空操作日志 // 清空操作日志
export function cleanOperlog() { export function cleanOperlog() {
return request({ return request({
url: '/monitor/operlog/clean', url: '/monitor/operlog/clean',
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,52 +1,52 @@
export interface OperLogQuery extends PageQuery { export interface OperLogQuery extends PageQuery {
title: string; title: string;
operName: string; operName: string;
businessType: string; businessType: string;
status: string; status: string;
orderByColumn: string; orderByColumn: string;
isAsc: string; isAsc: string;
} }
export interface OperLogVO extends BaseEntity { export interface OperLogVO extends BaseEntity {
operId: string | number; operId: string | number;
tenantId: string; tenantId: string;
title: string; title: string;
businessType: number; businessType: number;
businessTypes: number[] | undefined; businessTypes: number[] | undefined;
method: string; method: string;
requestMethod: string; requestMethod: string;
operatorType: number; operatorType: number;
operName: string; operName: string;
deptName: string; deptName: string;
operUrl: string; operUrl: string;
operIp: string; operIp: string;
operLocation: string; operLocation: string;
operParam: string; operParam: string;
jsonResult: string; jsonResult: string;
status: number; status: number;
errorMsg: string; errorMsg: string;
operTime: string; operTime: string;
costTime: number; costTime: number;
} }
export interface OperLogForm { export interface OperLogForm {
operId: number | string | undefined; operId: number | string | undefined;
tenantId: string | number | undefined; tenantId: string | number | undefined;
title: string; title: string;
businessType: number; businessType: number;
businessTypes: number[] | undefined; businessTypes: number[] | undefined;
method: string; method: string;
requestMethod: string; requestMethod: string;
operatorType: number; operatorType: number;
operName: string; operName: string;
deptName: string; deptName: string;
operUrl: string; operUrl: string;
operIp: string; operIp: string;
operLocation: string; operLocation: string;
operParam: string; operParam: string;
jsonResult: string; jsonResult: string;
status: number; status: number;
errorMsg: string; errorMsg: string;
operTime: string; operTime: string;
costTime: number; costTime: number;
} }

View File

@ -4,71 +4,71 @@ import { AxiosPromise } from 'axios';
// 查询参数列表 // 查询参数列表
export function listConfig(query: ConfigQuery): AxiosPromise<ConfigVO[]> { export function listConfig(query: ConfigQuery): AxiosPromise<ConfigVO[]> {
return request({ return request({
url: '/system/config/list', url: '/system/config/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询参数详细 // 查询参数详细
export function getConfig(configId: string | number): AxiosPromise<ConfigVO> { export function getConfig(configId: string | number): AxiosPromise<ConfigVO> {
return request({ return request({
url: '/system/config/' + configId, url: '/system/config/' + configId,
method: 'get' method: 'get'
}); });
} }
// 根据参数键名查询参数值 // 根据参数键名查询参数值
export function getConfigKey(configKey: string): AxiosPromise<ConfigVO> { export function getConfigKey(configKey: string): AxiosPromise<ConfigVO> {
return request({ return request({
url: '/system/config/configKey/' + configKey, url: '/system/config/configKey/' + configKey,
method: 'get' method: 'get'
}); });
} }
// 新增参数配置 // 新增参数配置
export function addConfig(data: ConfigForm) { export function addConfig(data: ConfigForm) {
return request({ return request({
url: '/system/config', url: '/system/config',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改参数配置 // 修改参数配置
export function updateConfig(data: ConfigForm) { export function updateConfig(data: ConfigForm) {
return request({ return request({
url: '/system/config', url: '/system/config',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 修改参数配置 // 修改参数配置
export function updateConfigByKey(key: string, value: any) { export function updateConfigByKey(key: string, value: any) {
return request({ return request({
url: '/system/config/updateByKey', url: '/system/config/updateByKey',
method: 'put', method: 'put',
data: { data: {
configKey: key, configKey: key,
configValue: value configValue: value
} }
}); });
} }
// 删除参数配置 // 删除参数配置
export function delConfig(configId: string | number | Array<string | number>) { export function delConfig(configId: string | number | Array<string | number>) {
return request({ return request({
url: '/system/config/' + configId, url: '/system/config/' + configId,
method: 'delete' method: 'delete'
}); });
} }
// 刷新参数缓存 // 刷新参数缓存
export function refreshCache() { export function refreshCache() {
return request({ return request({
url: '/system/config/refreshCache', url: '/system/config/refreshCache',
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,23 +1,23 @@
export interface ConfigVO extends BaseEntity { export interface ConfigVO extends BaseEntity {
configId: number | string; configId: number | string;
configName: string; configName: string;
configKey: string; configKey: string;
configValue: string; configValue: string;
configType: string; configType: string;
remark: string; remark: string;
} }
export interface ConfigForm { export interface ConfigForm {
configId: number | string | undefined; configId: number | string | undefined;
configName: string; configName: string;
configKey: string; configKey: string;
configValue: string; configValue: string;
configType: string; configType: string;
remark: string; remark: string;
} }
export interface ConfigQuery extends PageQuery { export interface ConfigQuery extends PageQuery {
configName: string; configName: string;
configKey: string; configKey: string;
configType: string; configType: string;
} }

View File

@ -4,59 +4,59 @@ import { DeptForm, DeptQuery, DeptVO } from './types';
// 查询部门列表 // 查询部门列表
export const listDept = (query?: DeptQuery) => { export const listDept = (query?: DeptQuery) => {
return request({ return request({
url: '/system/dept/list', url: '/system/dept/list',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
// 查询部门列表(排除节点) // 查询部门列表(排除节点)
export const listDeptExcludeChild = (deptId: string | number): AxiosPromise<DeptVO[]> => { export const listDeptExcludeChild = (deptId: string | number): AxiosPromise<DeptVO[]> => {
return request({ return request({
url: '/system/dept/list/exclude/' + deptId, url: '/system/dept/list/exclude/' + deptId,
method: 'get' method: 'get'
}); });
}; };
// 查询部门详细 // 查询部门详细
export const getDept = (deptId: string | number): AxiosPromise<DeptVO> => { export const getDept = (deptId: string | number): AxiosPromise<DeptVO> => {
return request({ return request({
url: '/system/dept/' + deptId, url: '/system/dept/' + deptId,
method: 'get' method: 'get'
}); });
}; };
// 查询部门下拉树结构 // 查询部门下拉树结构
export const treeselect = (): AxiosPromise<DeptVO[]> => { export const treeselect = (): AxiosPromise<DeptVO[]> => {
return request({ return request({
url: '/system/dept/treeselect', url: '/system/dept/treeselect',
method: 'get' method: 'get'
}); });
}; };
// 新增部门 // 新增部门
export const addDept = (data: DeptForm) => { export const addDept = (data: DeptForm) => {
return request({ return request({
url: '/system/dept', url: '/system/dept',
method: 'post', method: 'post',
data: data data: data
}); });
}; };
// 修改部门 // 修改部门
export const updateDept = (data: DeptForm) => { export const updateDept = (data: DeptForm) => {
return request({ return request({
url: '/system/dept', url: '/system/dept',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
// 删除部门 // 删除部门
export const delDept = (deptId: number | string) => { export const delDept = (deptId: number | string) => {
return request({ return request({
url: '/system/dept/' + deptId, url: '/system/dept/' + deptId,
method: 'delete' method: 'delete'
}); });
}; };

View File

@ -2,44 +2,44 @@
* 部门查询参数 * 部门查询参数
*/ */
export interface DeptQuery extends PageQuery { export interface DeptQuery extends PageQuery {
deptName?: string; deptName?: string;
status?: number; status?: number;
} }
/** /**
* 部门类型 * 部门类型
*/ */
export interface DeptVO extends BaseEntity { export interface DeptVO extends BaseEntity {
id: number | string; id: number | string;
parentName: string; parentName: string;
parentId: number | string; parentId: number | string;
children: DeptVO[]; children: DeptVO[];
deptId: number | string; deptId: number | string;
deptName: string; deptName: string;
orderNum: number; orderNum: number;
leader: string; leader: string;
phone: string; phone: string;
email: string; email: string;
status: string; status: string;
delFlag: string; delFlag: string;
ancestors: string; ancestors: string;
menuId: string | number; menuId: string | number;
} }
/** /**
* 部门表单类型 * 部门表单类型
*/ */
export interface DeptForm { export interface DeptForm {
parentName?: string; parentName?: string;
parentId?: number | string; parentId?: number | string;
children?: DeptForm[]; children?: DeptForm[];
deptId?: number | string; deptId?: number | string;
deptName?: string; deptName?: string;
orderNum?: number; orderNum?: number;
leader?: string; leader?: string;
phone?: string; phone?: string;
email?: string; email?: string;
status?: string; status?: string;
delFlag?: string; delFlag?: string;
ancestors?: string; ancestors?: string;
} }

View File

@ -3,51 +3,51 @@ import { AxiosPromise } from 'axios';
import { DictDataForm, DictDataQuery, DictDataVO } from './types'; import { DictDataForm, DictDataQuery, DictDataVO } from './types';
// 根据字典类型查询字典数据信息 // 根据字典类型查询字典数据信息
export function getDicts(dictType: string): AxiosPromise<DictDataVO[]> { export function getDicts(dictType: string): AxiosPromise<DictDataVO[]> {
return request({ return request({
url: '/system/dict/data/type/' + dictType, url: '/system/dict/data/type/' + dictType,
method: 'get' method: 'get'
}); });
} }
// 查询字典数据列表 // 查询字典数据列表
export function listData(query: DictDataQuery): AxiosPromise<DictDataVO[]> { export function listData(query: DictDataQuery): AxiosPromise<DictDataVO[]> {
return request({ return request({
url: '/system/dict/data/list', url: '/system/dict/data/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询字典数据详细 // 查询字典数据详细
export function getData(dictCode: string | number): AxiosPromise<DictDataVO> { export function getData(dictCode: string | number): AxiosPromise<DictDataVO> {
return request({ return request({
url: '/system/dict/data/' + dictCode, url: '/system/dict/data/' + dictCode,
method: 'get' method: 'get'
}); });
} }
// 新增字典数据 // 新增字典数据
export function addData(data: DictDataForm) { export function addData(data: DictDataForm) {
return request({ return request({
url: '/system/dict/data', url: '/system/dict/data',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改字典数据 // 修改字典数据
export function updateData(data: DictDataForm) { export function updateData(data: DictDataForm) {
return request({ return request({
url: '/system/dict/data', url: '/system/dict/data',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除字典数据 // 删除字典数据
export function delData(dictCode: string | number | Array<string | number>) { export function delData(dictCode: string | number | Array<string | number>) {
return request({ return request({
url: '/system/dict/data/' + dictCode, url: '/system/dict/data/' + dictCode,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,29 +1,29 @@
export interface DictDataQuery extends PageQuery { export interface DictDataQuery extends PageQuery {
dictName: string; dictName: string;
dictType: string; dictType: string;
status: string; status: string;
dictLabel: string; dictLabel: string;
} }
export interface DictDataVO extends BaseEntity { export interface DictDataVO extends BaseEntity {
dictCode: string; dictCode: string;
dictLabel: string; dictLabel: string;
dictValue: string; dictValue: string;
cssClass: string; cssClass: string;
listClass: ElTagType; listClass: ElTagType;
dictSort: number; dictSort: number;
status: string; status: string;
remark: string; remark: string;
} }
export interface DictDataForm { export interface DictDataForm {
dictType?: string; dictType?: string;
dictCode: string | undefined; dictCode: string | undefined;
dictLabel: string; dictLabel: string;
dictValue: string; dictValue: string;
cssClass: string; cssClass: string;
listClass: ElTagType; listClass: ElTagType;
dictSort: number; dictSort: number;
status: string; status: string;
remark: string; remark: string;
} }

View File

@ -4,59 +4,59 @@ import { AxiosPromise } from 'axios';
// 查询字典类型列表 // 查询字典类型列表
export function listType(query: DictTypeQuery): AxiosPromise<DictTypeVO[]> { export function listType(query: DictTypeQuery): AxiosPromise<DictTypeVO[]> {
return request({ return request({
url: '/system/dict/type/list', url: '/system/dict/type/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询字典类型详细 // 查询字典类型详细
export function getType(dictId: number | string): AxiosPromise<DictTypeVO> { export function getType(dictId: number | string): AxiosPromise<DictTypeVO> {
return request({ return request({
url: '/system/dict/type/' + dictId, url: '/system/dict/type/' + dictId,
method: 'get' method: 'get'
}); });
} }
// 新增字典类型 // 新增字典类型
export function addType(data: DictTypeForm) { export function addType(data: DictTypeForm) {
return request({ return request({
url: '/system/dict/type', url: '/system/dict/type',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改字典类型 // 修改字典类型
export function updateType(data: DictTypeForm) { export function updateType(data: DictTypeForm) {
return request({ return request({
url: '/system/dict/type', url: '/system/dict/type',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除字典类型 // 删除字典类型
export function delType(dictId: string | number | Array<string | number>) { export function delType(dictId: string | number | Array<string | number>) {
return request({ return request({
url: '/system/dict/type/' + dictId, url: '/system/dict/type/' + dictId,
method: 'delete' method: 'delete'
}); });
} }
// 刷新字典缓存 // 刷新字典缓存
export function refreshCache() { export function refreshCache() {
return request({ return request({
url: '/system/dict/type/refreshCache', url: '/system/dict/type/refreshCache',
method: 'delete' method: 'delete'
}); });
} }
// 获取字典选择框列表 // 获取字典选择框列表
export function optionselect(): AxiosPromise<DictTypeVO[]> { export function optionselect(): AxiosPromise<DictTypeVO[]> {
return request({ return request({
url: '/system/dict/type/optionselect', url: '/system/dict/type/optionselect',
method: 'get' method: 'get'
}); });
} }

View File

@ -1,21 +1,21 @@
export interface DictTypeVO extends BaseEntity { export interface DictTypeVO extends BaseEntity {
dictId: number | string; dictId: number | string;
dictName: string; dictName: string;
dictType: string; dictType: string;
status: string; status: string;
remark: string; remark: string;
} }
export interface DictTypeForm { export interface DictTypeForm {
dictId: number | string | undefined; dictId: number | string | undefined;
dictName: string; dictName: string;
dictType: string; dictType: string;
status: string; status: string;
remark: string; remark: string;
} }
export interface DictTypeQuery extends PageQuery { export interface DictTypeQuery extends PageQuery {
dictName: string; dictName: string;
dictType: string; dictType: string;
status: string; status: string;
} }

View File

@ -4,67 +4,67 @@ import { MenuQuery, MenuVO, MenuForm, MenuTreeOption, RoleMenuTree } from './typ
// 查询菜单列表 // 查询菜单列表
export const listMenu = (query?: MenuQuery): AxiosPromise<MenuVO[]> => { export const listMenu = (query?: MenuQuery): AxiosPromise<MenuVO[]> => {
return request({ return request({
url: '/system/menu/list', url: '/system/menu/list',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
// 查询菜单详细 // 查询菜单详细
export const getMenu = (menuId: string | number): AxiosPromise<MenuVO> => { export const getMenu = (menuId: string | number): AxiosPromise<MenuVO> => {
return request({ return request({
url: '/system/menu/' + menuId, url: '/system/menu/' + menuId,
method: 'get' method: 'get'
}); });
}; };
// 查询菜单下拉树结构 // 查询菜单下拉树结构
export const treeselect = (): AxiosPromise<MenuTreeOption[]> => { export const treeselect = (): AxiosPromise<MenuTreeOption[]> => {
return request({ return request({
url: '/system/menu/treeselect', url: '/system/menu/treeselect',
method: 'get' method: 'get'
}); });
}; };
// 根据角色ID查询菜单下拉树结构 // 根据角色ID查询菜单下拉树结构
export const roleMenuTreeselect = (roleId: string | number): AxiosPromise<RoleMenuTree> => { export const roleMenuTreeselect = (roleId: string | number): AxiosPromise<RoleMenuTree> => {
return request({ return request({
url: '/system/menu/roleMenuTreeselect/' + roleId, url: '/system/menu/roleMenuTreeselect/' + roleId,
method: 'get' method: 'get'
}); });
}; };
// 根据角色ID查询菜单下拉树结构 // 根据角色ID查询菜单下拉树结构
export const tenantPackageMenuTreeselect = (packageId: string | number): AxiosPromise<RoleMenuTree> => { export const tenantPackageMenuTreeselect = (packageId: string | number): AxiosPromise<RoleMenuTree> => {
return request({ return request({
url: '/system/menu/tenantPackageMenuTreeselect/' + packageId, url: '/system/menu/tenantPackageMenuTreeselect/' + packageId,
method: 'get' method: 'get'
}); });
}; };
// 新增菜单 // 新增菜单
export const addMenu = (data: MenuForm) => { export const addMenu = (data: MenuForm) => {
return request({ return request({
url: '/system/menu', url: '/system/menu',
method: 'post', method: 'post',
data: data data: data
}); });
}; };
// 修改菜单 // 修改菜单
export const updateMenu = (data: MenuForm) => { export const updateMenu = (data: MenuForm) => {
return request({ return request({
url: '/system/menu', url: '/system/menu',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
// 删除菜单 // 删除菜单
export const delMenu = (menuId: string | number) => { export const delMenu = (menuId: string | number) => {
return request({ return request({
url: '/system/menu/' + menuId, url: '/system/menu/' + menuId,
method: 'delete' method: 'delete'
}); });
}; };

View File

@ -4,66 +4,66 @@ import { MenuTypeEnum } from '@/enums/MenuTypeEnum';
* 菜单树形结构类型 * 菜单树形结构类型
*/ */
export interface MenuTreeOption { export interface MenuTreeOption {
id: string | number; id: string | number;
label: string; label: string;
parentId: string | number; parentId: string | number;
weight: number; weight: number;
children?: MenuTreeOption[]; children?: MenuTreeOption[];
} }
export interface RoleMenuTree { export interface RoleMenuTree {
menus: MenuTreeOption[]; menus: MenuTreeOption[];
checkedKeys: string[]; checkedKeys: string[];
} }
/** /**
* 菜单查询参数类型 * 菜单查询参数类型
*/ */
export interface MenuQuery { export interface MenuQuery {
keywords?: string; keywords?: string;
menuName?: string; menuName?: string;
status?: string; status?: string;
} }
/** /**
* 菜单视图对象类型 * 菜单视图对象类型
*/ */
export interface MenuVO extends BaseEntity { export interface MenuVO extends BaseEntity {
parentName: string; parentName: string;
parentId: string | number; parentId: string | number;
children: MenuVO[]; children: MenuVO[];
menuId: string | number; menuId: string | number;
menuName: string; menuName: string;
orderNum: number; orderNum: number;
path: string; path: string;
component: string; component: string;
queryParam: string; queryParam: string;
isFrame: string; isFrame: string;
isCache: string; isCache: string;
menuType: MenuTypeEnum; menuType: MenuTypeEnum;
visible: string; visible: string;
status: string; status: string;
icon: string; icon: string;
remark: string; remark: string;
} }
export interface MenuForm { export interface MenuForm {
parentName?: string; parentName?: string;
parentId?: string | number; parentId?: string | number;
children?: MenuForm[]; children?: MenuForm[];
menuId?: string | number; menuId?: string | number;
menuName: string; menuName: string;
orderNum: number; orderNum: number;
path: string; path: string;
component?: string; component?: string;
queryParam?: string; queryParam?: string;
isFrame?: string; isFrame?: string;
isCache?: string; isCache?: string;
menuType?: MenuTypeEnum; menuType?: MenuTypeEnum;
visible?: string; visible?: string;
status?: string; status?: string;
icon?: string; icon?: string;
remark?: string; remark?: string;
query?: string; query?: string;
perms?: string; perms?: string;
} }

View File

@ -3,43 +3,43 @@ import { NoticeForm, NoticeQuery, NoticeVO } from './types';
import { AxiosPromise } from 'axios'; import { AxiosPromise } from 'axios';
// 查询公告列表 // 查询公告列表
export function listNotice(query: NoticeQuery): AxiosPromise<NoticeVO[]> { export function listNotice(query: NoticeQuery): AxiosPromise<NoticeVO[]> {
return request({ return request({
url: '/system/notice/list', url: '/system/notice/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询公告详细 // 查询公告详细
export function getNotice(noticeId: string | number): AxiosPromise<NoticeVO> { export function getNotice(noticeId: string | number): AxiosPromise<NoticeVO> {
return request({ return request({
url: '/system/notice/' + noticeId, url: '/system/notice/' + noticeId,
method: 'get' method: 'get'
}); });
} }
// 新增公告 // 新增公告
export function addNotice(data: NoticeForm) { export function addNotice(data: NoticeForm) {
return request({ return request({
url: '/system/notice', url: '/system/notice',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改公告 // 修改公告
export function updateNotice(data: NoticeForm) { export function updateNotice(data: NoticeForm) {
return request({ return request({
url: '/system/notice', url: '/system/notice',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除公告 // 删除公告
export function delNotice(noticeId: string | number | Array<string | number>) { export function delNotice(noticeId: string | number | Array<string | number>) {
return request({ return request({
url: '/system/notice/' + noticeId, url: '/system/notice/' + noticeId,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,26 +1,26 @@
export interface NoticeVO extends BaseEntity { export interface NoticeVO extends BaseEntity {
noticeId: number; noticeId: number;
noticeTitle: string; noticeTitle: string;
noticeType: string; noticeType: string;
noticeContent: string; noticeContent: string;
status: string; status: string;
remark: string; remark: string;
createByName: string; createByName: string;
} }
export interface NoticeQuery extends PageQuery { export interface NoticeQuery extends PageQuery {
noticeTitle: string; noticeTitle: string;
createByName: string; createByName: string;
status: string; status: string;
noticeType: string; noticeType: string;
} }
export interface NoticeForm { export interface NoticeForm {
noticeId: number | string | undefined; noticeId: number | string | undefined;
noticeTitle: string; noticeTitle: string;
noticeType: string; noticeType: string;
noticeContent: string; noticeContent: string;
status: string; status: string;
remark: string; remark: string;
createByName: string; createByName: string;
} }

View File

@ -4,25 +4,25 @@ import { AxiosPromise } from 'axios';
// 查询OSS对象存储列表 // 查询OSS对象存储列表
export function listOss(query: OssQuery): AxiosPromise<OssVO[]> { export function listOss(query: OssQuery): AxiosPromise<OssVO[]> {
return request({ return request({
url: '/system/oss/list', url: '/system/oss/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询OSS对象基于id串 // 查询OSS对象基于id串
export function listByIds(ossId: string | number): AxiosPromise<OssVO[]> { export function listByIds(ossId: string | number): AxiosPromise<OssVO[]> {
return request({ return request({
url: '/system/oss/listByIds/' + ossId, url: '/system/oss/listByIds/' + ossId,
method: 'get' method: 'get'
}); });
} }
// 删除OSS对象存储 // 删除OSS对象存储
export function delOss(ossId: string | number | Array<string | number>) { export function delOss(ossId: string | number | Array<string | number>) {
return request({ return request({
url: '/system/oss/' + ossId, url: '/system/oss/' + ossId,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,22 +1,22 @@
export interface OssVO extends BaseEntity { export interface OssVO extends BaseEntity {
ossId: string | number; ossId: string | number;
fileName: string; fileName: string;
originalName: string; originalName: string;
fileSuffix: string; fileSuffix: string;
url: string; url: string;
createByName: string; createByName: string;
service: string; service: string;
} }
export interface OssQuery extends PageQuery { export interface OssQuery extends PageQuery {
fileName: string; fileName: string;
originalName: string; originalName: string;
fileSuffix: string; fileSuffix: string;
createTime: string; createTime: string;
service: string; service: string;
orderByColumn: string; orderByColumn: string;
isAsc: string; isAsc: string;
} }
export interface OssForm { export interface OssForm {
file: undefined | string; file: undefined | string;
} }

View File

@ -4,57 +4,57 @@ import { AxiosPromise } from 'axios';
// 查询对象存储配置列表 // 查询对象存储配置列表
export function listOssConfig(query: OssConfigQuery): AxiosPromise<OssConfigVO[]> { export function listOssConfig(query: OssConfigQuery): AxiosPromise<OssConfigVO[]> {
return request({ return request({
url: '/system/oss/config/list', url: '/system/oss/config/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询对象存储配置详细 // 查询对象存储配置详细
export function getOssConfig(ossConfigId: string | number): AxiosPromise<OssConfigVO> { export function getOssConfig(ossConfigId: string | number): AxiosPromise<OssConfigVO> {
return request({ return request({
url: '/system/oss/config/' + ossConfigId, url: '/system/oss/config/' + ossConfigId,
method: 'get' method: 'get'
}); });
} }
// 新增对象存储配置 // 新增对象存储配置
export function addOssConfig(data: OssConfigForm) { export function addOssConfig(data: OssConfigForm) {
return request({ return request({
url: '/system/oss/config', url: '/system/oss/config',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改对象存储配置 // 修改对象存储配置
export function updateOssConfig(data: OssConfigForm) { export function updateOssConfig(data: OssConfigForm) {
return request({ return request({
url: '/system/oss/config', url: '/system/oss/config',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除对象存储配置 // 删除对象存储配置
export function delOssConfig(ossConfigId: string | number | Array<string | number>) { export function delOssConfig(ossConfigId: string | number | Array<string | number>) {
return request({ return request({
url: '/system/oss/config/' + ossConfigId, url: '/system/oss/config/' + ossConfigId,
method: 'delete' method: 'delete'
}); });
} }
// 对象存储状态修改 // 对象存储状态修改
export function changeOssConfigStatus(ossConfigId: string | number, status: string, configKey: string) { export function changeOssConfigStatus(ossConfigId: string | number, status: string, configKey: string) {
const data = { const data = {
ossConfigId, ossConfigId,
status, status,
configKey configKey
}; };
return request({ return request({
url: '/system/oss/config/changeStatus', url: '/system/oss/config/changeStatus',
method: 'put', method: 'put',
data: data data: data
}); });
} }

View File

@ -1,38 +1,38 @@
export interface OssConfigVO extends BaseEntity { export interface OssConfigVO extends BaseEntity {
ossConfigId: number | string; ossConfigId: number | string;
configKey: string; configKey: string;
accessKey: string; accessKey: string;
secretKey: string; secretKey: string;
bucketName: string; bucketName: string;
prefix: string; prefix: string;
endpoint: string; endpoint: string;
domain: string; domain: string;
isHttps: string; isHttps: string;
region: string; region: string;
status: string; status: string;
ext1: string; ext1: string;
remark: string; remark: string;
accessPolicy: string; accessPolicy: string;
} }
export interface OssConfigQuery extends PageQuery { export interface OssConfigQuery extends PageQuery {
configKey: string; configKey: string;
bucketName: string; bucketName: string;
status: string; status: string;
} }
export interface OssConfigForm { export interface OssConfigForm {
ossConfigId: string | number | undefined; ossConfigId: string | number | undefined;
configKey: string; configKey: string;
accessKey: string; accessKey: string;
secretKey: string; secretKey: string;
bucketName: string; bucketName: string;
prefix: string; prefix: string;
endpoint: string; endpoint: string;
domain: string; domain: string;
isHttps: string; isHttps: string;
accessPolicy: string; accessPolicy: string;
region: string; region: string;
status: string; status: string;
remark: string; remark: string;
} }

View File

@ -4,43 +4,43 @@ import { AxiosPromise } from 'axios';
// 查询岗位列表 // 查询岗位列表
export function listPost(query: PostQuery): AxiosPromise<PostVO[]> { export function listPost(query: PostQuery): AxiosPromise<PostVO[]> {
return request({ return request({
url: '/system/post/list', url: '/system/post/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询岗位详细 // 查询岗位详细
export function getPost(postId: string | number): AxiosPromise<PostVO> { export function getPost(postId: string | number): AxiosPromise<PostVO> {
return request({ return request({
url: '/system/post/' + postId, url: '/system/post/' + postId,
method: 'get' method: 'get'
}); });
} }
// 新增岗位 // 新增岗位
export function addPost(data: PostForm) { export function addPost(data: PostForm) {
return request({ return request({
url: '/system/post', url: '/system/post',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改岗位 // 修改岗位
export function updatePost(data: PostForm) { export function updatePost(data: PostForm) {
return request({ return request({
url: '/system/post', url: '/system/post',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除岗位 // 删除岗位
export function delPost(postId: string | number | (string | number)[]) { export function delPost(postId: string | number | (string | number)[]) {
return request({ return request({
url: '/system/post/' + postId, url: '/system/post/' + postId,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,23 +1,23 @@
export interface PostVO extends BaseEntity { export interface PostVO extends BaseEntity {
postId: number | string; postId: number | string;
postCode: string; postCode: string;
postName: string; postName: string;
postSort: number; postSort: number;
status: string; status: string;
remark: string; remark: string;
} }
export interface PostForm { export interface PostForm {
postId: number | string | undefined; postId: number | string | undefined;
postCode: string; postCode: string;
postName: string; postName: string;
postSort: number; postSort: number;
status: string; status: string;
remark: string; remark: string;
} }
export interface PostQuery extends PageQuery { export interface PostQuery extends PageQuery {
postCode: string; postCode: string;
postName: string; postName: string;
status: string; status: string;
} }

View File

@ -5,32 +5,32 @@ import { RoleQuery, RoleVO, RoleDeptTree } from './types';
import request from '@/utils/request'; import request from '@/utils/request';
export const listRole = (query: RoleQuery): AxiosPromise<RoleVO[]> => { export const listRole = (query: RoleQuery): AxiosPromise<RoleVO[]> => {
return request({ return request({
url: '/system/role/list', url: '/system/role/list',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
/** /**
* 查询角色详细 * 查询角色详细
*/ */
export const getRole = (roleId: string | number): AxiosPromise<RoleVO> => { export const getRole = (roleId: string | number): AxiosPromise<RoleVO> => {
return request({ return request({
url: '/system/role/' + roleId, url: '/system/role/' + roleId,
method: 'get' method: 'get'
}); });
}; };
/** /**
* 新增角色 * 新增角色
*/ */
export const addRole = (data: any) => { export const addRole = (data: any) => {
return request({ return request({
url: '/system/role', url: '/system/role',
method: 'post', method: 'post',
data: data data: data
}); });
}; };
/** /**
@ -38,107 +38,107 @@ export const addRole = (data: any) => {
* @param data * @param data
*/ */
export const updateRole = (data: any) => { export const updateRole = (data: any) => {
return request({ return request({
url: '/system/role', url: '/system/role',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
/** /**
* 角色数据权限 * 角色数据权限
*/ */
export const dataScope = (data: any) => { export const dataScope = (data: any) => {
return request({ return request({
url: '/system/role/dataScope', url: '/system/role/dataScope',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
/** /**
* 角色状态修改 * 角色状态修改
*/ */
export const changeRoleStatus = (roleId: string | number, status: string) => { export const changeRoleStatus = (roleId: string | number, status: string) => {
const data = { const data = {
roleId, roleId,
status status
}; };
return request({ return request({
url: '/system/role/changeStatus', url: '/system/role/changeStatus',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
/** /**
* 删除角色 * 删除角色
*/ */
export const delRole = (roleId: Array<string | number> | string | number) => { export const delRole = (roleId: Array<string | number> | string | number) => {
return request({ return request({
url: '/system/role/' + roleId, url: '/system/role/' + roleId,
method: 'delete' method: 'delete'
}); });
}; };
/** /**
* 查询角色已授权用户列表 * 查询角色已授权用户列表
*/ */
export const allocatedUserList = (query: UserQuery): AxiosPromise<UserVO[]> => { export const allocatedUserList = (query: UserQuery): AxiosPromise<UserVO[]> => {
return request({ return request({
url: '/system/role/authUser/allocatedList', url: '/system/role/authUser/allocatedList',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
/** /**
* 查询角色未授权用户列表 * 查询角色未授权用户列表
*/ */
export const unallocatedUserList = (query: UserQuery): AxiosPromise<UserVO[]> => { export const unallocatedUserList = (query: UserQuery): AxiosPromise<UserVO[]> => {
return request({ return request({
url: '/system/role/authUser/unallocatedList', url: '/system/role/authUser/unallocatedList',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
/** /**
* 取消用户授权角色 * 取消用户授权角色
*/ */
export const authUserCancel = (data: any) => { export const authUserCancel = (data: any) => {
return request({ return request({
url: '/system/role/authUser/cancel', url: '/system/role/authUser/cancel',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
/** /**
* 批量取消用户授权角色 * 批量取消用户授权角色
*/ */
export const authUserCancelAll = (data: any) => { export const authUserCancelAll = (data: any) => {
return request({ return request({
url: '/system/role/authUser/cancelAll', url: '/system/role/authUser/cancelAll',
method: 'put', method: 'put',
params: data params: data
}); });
}; };
/** /**
* 授权用户选择 * 授权用户选择
*/ */
export const authUserSelectAll = (data: any) => { export const authUserSelectAll = (data: any) => {
return request({ return request({
url: '/system/role/authUser/selectAll', url: '/system/role/authUser/selectAll',
method: 'put', method: 'put',
params: data params: data
}); });
}; };
// 根据角色ID查询部门树结构 // 根据角色ID查询部门树结构
export const deptTreeSelect = (roleId: string | number): AxiosPromise<RoleDeptTree> => { export const deptTreeSelect = (roleId: string | number): AxiosPromise<RoleDeptTree> => {
return request({ return request({
url: '/system/role/deptTree/' + roleId, url: '/system/role/deptTree/' + roleId,
method: 'get' method: 'get'
}); });
}; };

View File

@ -2,51 +2,51 @@
* 菜单树形结构类型 * 菜单树形结构类型
*/ */
export interface DeptTreeOption { export interface DeptTreeOption {
id: string; id: string;
label: string; label: string;
parentId: string; parentId: string;
weight: number; weight: number;
children?: DeptTreeOption[]; children?: DeptTreeOption[];
} }
export interface RoleDeptTree { export interface RoleDeptTree {
checkedKeys: string[]; checkedKeys: string[];
depts: DeptTreeOption[]; depts: DeptTreeOption[];
} }
export interface RoleVO extends BaseEntity { export interface RoleVO extends BaseEntity {
roleId: string | number; roleId: string | number;
roleName: string; roleName: string;
roleKey: string; roleKey: string;
roleSort: number; roleSort: number;
dataScope: string; dataScope: string;
menuCheckStrictly: boolean; menuCheckStrictly: boolean;
deptCheckStrictly: boolean; deptCheckStrictly: boolean;
status: string; status: string;
delFlag: string; delFlag: string;
remark?: any; remark?: any;
flag: boolean; flag: boolean;
menuIds?: Array<string | number>; menuIds?: Array<string | number>;
deptIds?: Array<string | number>; deptIds?: Array<string | number>;
admin: boolean; admin: boolean;
} }
export interface RoleQuery extends PageQuery { export interface RoleQuery extends PageQuery {
roleName: string; roleName: string;
roleKey: string; roleKey: string;
status: string; status: string;
} }
export interface RoleForm { export interface RoleForm {
roleName: string; roleName: string;
roleKey: string; roleKey: string;
roleSort: number; roleSort: number;
status: string; status: string;
menuCheckStrictly: boolean; menuCheckStrictly: boolean;
deptCheckStrictly: boolean; deptCheckStrictly: boolean;
remark: string; remark: string;
dataScope?: number; dataScope?: number;
roleId: string | undefined; roleId: string | undefined;
menuIds: Array<string | number>; menuIds: Array<string | number>;
deptIds: Array<string | number>; deptIds: Array<string | number>;
} }

View File

@ -4,86 +4,86 @@ import { AxiosPromise } from 'axios';
// 查询租户列表 // 查询租户列表
export function listTenant(query: TenantQuery): AxiosPromise<TenantVO[]> { export function listTenant(query: TenantQuery): AxiosPromise<TenantVO[]> {
return request({ return request({
url: '/system/tenant/list', url: '/system/tenant/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询租户详细 // 查询租户详细
export function getTenant(id: string | number): AxiosPromise<TenantVO> { export function getTenant(id: string | number): AxiosPromise<TenantVO> {
return request({ return request({
url: '/system/tenant/' + id, url: '/system/tenant/' + id,
method: 'get' method: 'get'
}); });
} }
// 新增租户 // 新增租户
export function addTenant(data: TenantForm) { export function addTenant(data: TenantForm) {
return request({ return request({
url: '/system/tenant', url: '/system/tenant',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改租户 // 修改租户
export function updateTenant(data: TenantForm) { export function updateTenant(data: TenantForm) {
return request({ return request({
url: '/system/tenant', url: '/system/tenant',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 租户状态修改 // 租户状态修改
export function changeTenantStatus(id: string | number, tenantId: string | number, status: string) { export function changeTenantStatus(id: string | number, tenantId: string | number, status: string) {
const data = { const data = {
id, id,
tenantId, tenantId,
status status
}; };
return request({ return request({
url: '/system/tenant/changeStatus', url: '/system/tenant/changeStatus',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除租户 // 删除租户
export function delTenant(id: string | number | Array<string | number>) { export function delTenant(id: string | number | Array<string | number>) {
return request({ return request({
url: '/system/tenant/' + id, url: '/system/tenant/' + id,
method: 'delete' method: 'delete'
}); });
} }
// 动态切换租户 // 动态切换租户
export function dynamicTenant(tenantId: string | number) { export function dynamicTenant(tenantId: string | number) {
return request({ return request({
url: '/system/tenant/dynamic/' + tenantId, url: '/system/tenant/dynamic/' + tenantId,
method: 'get' method: 'get'
}); });
} }
// 清除动态租户 // 清除动态租户
export function dynamicClear() { export function dynamicClear() {
return request({ return request({
url: '/system/tenant/dynamic/clear', url: '/system/tenant/dynamic/clear',
method: 'get' method: 'get'
}); });
} }
// 同步租户套餐 // 同步租户套餐
export function syncTenantPackage(tenantId: string | number, packageId: string | number) { export function syncTenantPackage(tenantId: string | number, packageId: string | number) {
const data = { const data = {
tenantId, tenantId,
packageId packageId
}; };
return request({ return request({
url: '/system/tenant/syncTenantPackage', url: '/system/tenant/syncTenantPackage',
method: 'get', method: 'get',
params: data params: data
}); });
} }

View File

@ -1,46 +1,46 @@
export interface TenantVO extends BaseEntity { export interface TenantVO extends BaseEntity {
id: number | string; id: number | string;
tenantId: number | string; tenantId: number | string;
username: string; username: string;
contactUserName: string; contactUserName: string;
contactPhone: string; contactPhone: string;
companyName: string; companyName: string;
licenseNumber: string; licenseNumber: string;
address: string; address: string;
domain: string; domain: string;
intro: string; intro: string;
remark: string; remark: string;
packageId: string | number; packageId: string | number;
expireTime: string; expireTime: string;
accountCount: number; accountCount: number;
status: string; status: string;
} }
export interface TenantQuery extends PageQuery { export interface TenantQuery extends PageQuery {
tenantId: string | number; tenantId: string | number;
contactUserName: string; contactUserName: string;
contactPhone: string; contactPhone: string;
companyName: string; companyName: string;
} }
export interface TenantForm { export interface TenantForm {
id: number | string | undefined; id: number | string | undefined;
tenantId: number | string | undefined; tenantId: number | string | undefined;
username: string; username: string;
password: string; password: string;
contactUserName: string; contactUserName: string;
contactPhone: string; contactPhone: string;
companyName: string; companyName: string;
licenseNumber: string; licenseNumber: string;
domain: string; domain: string;
address: string; address: string;
intro: string; intro: string;
remark: string; remark: string;
packageId: string | number; packageId: string | number;
expireTime: string; expireTime: string;
accountCount: number; accountCount: number;
status: string; status: string;
} }

View File

@ -4,56 +4,56 @@ import { AxiosPromise } from 'axios';
// 查询租户套餐列表 // 查询租户套餐列表
export function listTenantPackage(query?: TenantPkgQuery): AxiosPromise<TenantPkgVO[]> { export function listTenantPackage(query?: TenantPkgQuery): AxiosPromise<TenantPkgVO[]> {
return request({ return request({
url: '/system/tenant/package/list', url: '/system/tenant/package/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
// 查询租户套餐详细 // 查询租户套餐详细
export function getTenantPackage(packageId: string | number): AxiosPromise<TenantPkgVO> { export function getTenantPackage(packageId: string | number): AxiosPromise<TenantPkgVO> {
return request({ return request({
url: '/system/tenant/package/' + packageId, url: '/system/tenant/package/' + packageId,
method: 'get' method: 'get'
}); });
} }
// 新增租户套餐 // 新增租户套餐
export function addTenantPackage(data: TenantPkgForm) { export function addTenantPackage(data: TenantPkgForm) {
return request({ return request({
url: '/system/tenant/package', url: '/system/tenant/package',
method: 'post', method: 'post',
data: data data: data
}); });
} }
// 修改租户套餐 // 修改租户套餐
export function updateTenantPackage(data: TenantPkgForm) { export function updateTenantPackage(data: TenantPkgForm) {
return request({ return request({
url: '/system/tenant/package', url: '/system/tenant/package',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 租户套餐状态修改 // 租户套餐状态修改
export function changePackageStatus(packageId: number | string, status: string) { export function changePackageStatus(packageId: number | string, status: string) {
const data = { const data = {
packageId, packageId,
status status
}; };
return request({ return request({
url: '/system/tenant/package/changeStatus', url: '/system/tenant/package/changeStatus',
method: 'put', method: 'put',
data: data data: data
}); });
} }
// 删除租户套餐 // 删除租户套餐
export function delTenantPackage(packageId: string | number | Array<string | number>) { export function delTenantPackage(packageId: string | number | Array<string | number>) {
return request({ return request({
url: '/system/tenant/package/' + packageId, url: '/system/tenant/package/' + packageId,
method: 'delete' method: 'delete'
}); });
} }

View File

@ -1,22 +1,22 @@
export interface TenantPkgVO extends BaseEntity { export interface TenantPkgVO extends BaseEntity {
packageId: string | number; packageId: string | number;
packageName: string; packageName: string;
menuIds: string; menuIds: string;
remark: string; remark: string;
menuCheckStrictly: boolean; menuCheckStrictly: boolean;
status: string; status: string;
} }
export interface TenantPkgQuery extends PageQuery { export interface TenantPkgQuery extends PageQuery {
packageName: string; packageName: string;
status: string; status: string;
} }
export interface TenantPkgForm { export interface TenantPkgForm {
packageId: string | number | undefined; packageId: string | number | undefined;
packageName: string; packageName: string;
menuIds: string; menuIds: string;
remark: string; remark: string;
menuCheckStrictly: boolean; menuCheckStrictly: boolean;
status: string; status: string;
} }

View File

@ -10,11 +10,11 @@ import { parseStrEmpty } from '@/utils/ruoyi';
* @param query * @param query
*/ */
export function listUser(query: UserQuery): AxiosPromise<UserVO[]> { export function listUser(query: UserQuery): AxiosPromise<UserVO[]> {
return request({ return request({
url: '/system/user/list', url: '/system/user/list',
method: 'get', method: 'get',
params: query params: query
}); });
} }
/** /**
@ -22,32 +22,32 @@ export function listUser(query: UserQuery): AxiosPromise<UserVO[]> {
* @param userId * @param userId
*/ */
export function getUser(userId?: string | number): AxiosPromise<UserInfoVO> { export function getUser(userId?: string | number): AxiosPromise<UserInfoVO> {
return request({ return request({
url: '/system/user/' + parseStrEmpty(userId), url: '/system/user/' + parseStrEmpty(userId),
method: 'get' method: 'get'
}); });
} }
/** /**
* 新增用户 * 新增用户
*/ */
export function addUser(data: UserForm) { export function addUser(data: UserForm) {
return request({ return request({
url: '/system/user', url: '/system/user',
method: 'post', method: 'post',
data: data data: data
}); });
} }
/** /**
* 修改用户 * 修改用户
*/ */
export function updateUser(data: UserForm) { export function updateUser(data: UserForm) {
return request({ return request({
url: '/system/user', url: '/system/user',
method: 'put', method: 'put',
data: data data: data
}); });
} }
/** /**
@ -55,10 +55,10 @@ export function updateUser(data: UserForm) {
* @param userId 用户ID * @param userId 用户ID
*/ */
export function delUser(userId: Array<string | number> | string | number) { export function delUser(userId: Array<string | number> | string | number) {
return request({ return request({
url: '/system/user/' + userId, url: '/system/user/' + userId,
method: 'delete' method: 'delete'
}); });
} }
/** /**
@ -67,15 +67,15 @@ export function delUser(userId: Array<string | number> | string | number) {
* @param password 密码 * @param password 密码
*/ */
export function resetUserPwd(userId: string | number, password: string) { export function resetUserPwd(userId: string | number, password: string) {
const data = { const data = {
userId, userId,
password password
}; };
return request({ return request({
url: '/system/user/resetPwd', url: '/system/user/resetPwd',
method: 'put', method: 'put',
data: data data: data
}); });
} }
/** /**
@ -84,25 +84,25 @@ export function resetUserPwd(userId: string | number, password: string) {
* @param status 用户状态 * @param status 用户状态
*/ */
export function changeUserStatus(userId: number | string, status: string) { export function changeUserStatus(userId: number | string, status: string) {
const data = { const data = {
userId, userId,
status status
}; };
return request({ return request({
url: '/system/user/changeStatus', url: '/system/user/changeStatus',
method: 'put', method: 'put',
data: data data: data
}); });
} }
/** /**
* 查询用户个人信息 * 查询用户个人信息
*/ */
export function getUserProfile(): AxiosPromise<UserInfoVO> { export function getUserProfile(): AxiosPromise<UserInfoVO> {
return request({ return request({
url: '/system/user/profile', url: '/system/user/profile',
method: 'get' method: 'get'
}); });
} }
/** /**
@ -110,11 +110,11 @@ export function getUserProfile(): AxiosPromise<UserInfoVO> {
* @param data 用户信息 * @param data 用户信息
*/ */
export function updateUserProfile(data: UserForm) { export function updateUserProfile(data: UserForm) {
return request({ return request({
url: '/system/user/profile', url: '/system/user/profile',
method: 'put', method: 'put',
data: data data: data
}); });
} }
/** /**
@ -123,15 +123,15 @@ export function updateUserProfile(data: UserForm) {
* @param newPassword 新密码 * @param newPassword 新密码
*/ */
export function updateUserPwd(oldPassword: string, newPassword: string) { export function updateUserPwd(oldPassword: string, newPassword: string) {
const data = { const data = {
oldPassword, oldPassword,
newPassword newPassword
}; };
return request({ return request({
url: '/system/user/profile/updatePwd', url: '/system/user/profile/updatePwd',
method: 'put', method: 'put',
params: data params: data
}); });
} }
/** /**
@ -139,11 +139,11 @@ export function updateUserPwd(oldPassword: string, newPassword: string) {
* @param data 头像文件 * @param data 头像文件
*/ */
export function uploadAvatar(data: FormData) { export function uploadAvatar(data: FormData) {
return request({ return request({
url: '/system/user/profile/avatar', url: '/system/user/profile/avatar',
method: 'post', method: 'post',
data: data data: data
}); });
} }
/** /**
@ -151,10 +151,10 @@ export function uploadAvatar(data: FormData) {
* @param userId 用户ID * @param userId 用户ID
*/ */
export function getAuthRole(userId: string | number): AxiosPromise<{ user: UserVO; roles: RoleVO[] }> { export function getAuthRole(userId: string | number): AxiosPromise<{ user: UserVO; roles: RoleVO[] }> {
return request({ return request({
url: '/system/user/authRole/' + userId, url: '/system/user/authRole/' + userId,
method: 'get' method: 'get'
}); });
} }
/** /**
@ -162,19 +162,19 @@ export function getAuthRole(userId: string | number): AxiosPromise<{ user: UserV
* @param data 用户ID * @param data 用户ID
*/ */
export function updateAuthRole(data: { userId: string; roleIds: string }) { export function updateAuthRole(data: { userId: string; roleIds: string }) {
return request({ return request({
url: '/system/user/authRole', url: '/system/user/authRole',
method: 'put', method: 'put',
params: data params: data
}); });
} }
/** /**
* 查询部门下拉树结构 * 查询部门下拉树结构
*/ */
export function deptTreeSelect(): AxiosPromise<DeptVO[]> { export function deptTreeSelect(): AxiosPromise<DeptVO[]> {
return request({ return request({
url: '/system/user/deptTree', url: '/system/user/deptTree',
method: 'get' method: 'get'
}); });
} }

View File

@ -6,79 +6,79 @@ import { PostVO } from '@/api/system/post/types';
* 用户信息 * 用户信息
*/ */
export interface UserInfo { export interface UserInfo {
user: UserVO; user: UserVO;
roles: string[]; roles: string[];
permissions: string[]; permissions: string[];
} }
/** /**
* 用户查询对象类型 * 用户查询对象类型
*/ */
export interface UserQuery extends PageQuery { export interface UserQuery extends PageQuery {
userName?: string; userName?: string;
phonenumber?: string; phonenumber?: string;
status?: string; status?: string;
deptId?: string | number; deptId?: string | number;
roleId?: string | number; roleId?: string | number;
} }
/** /**
* 用户返回对象 * 用户返回对象
*/ */
export interface UserVO extends BaseEntity { export interface UserVO extends BaseEntity {
userId: string | number; userId: string | number;
deptId: number; deptId: number;
userName: string; userName: string;
nickName: string; nickName: string;
userType: string; userType: string;
email: string; email: string;
phonenumber: string; phonenumber: string;
sex: string; sex: string;
avatar: string; avatar: string;
status: string; status: string;
delFlag: string; delFlag: string;
loginIp: string; loginIp: string;
loginDate: string; loginDate: string;
remark: string; remark: string;
dept: DeptVO; dept: DeptVO;
roles: RoleVO[]; roles: RoleVO[];
roleIds: any; roleIds: any;
postIds: any; postIds: any;
roleId: any; roleId: any;
admin: boolean; admin: boolean;
} }
/** /**
* 用户表单类型 * 用户表单类型
*/ */
export interface UserForm { export interface UserForm {
id?: string; id?: string;
userId?: string; userId?: string;
deptId?: number; deptId?: number;
userName: string; userName: string;
nickName?: string; nickName?: string;
password: string; password: string;
phonenumber?: string; phonenumber?: string;
email?: string; email?: string;
sex?: string; sex?: string;
status: string; status: string;
remark?: string; remark?: string;
postIds: string[]; postIds: string[];
roleIds: string[]; roleIds: string[];
} }
export interface UserInfoVO { export interface UserInfoVO {
user: UserVO; user: UserVO;
roles: RoleVO[]; roles: RoleVO[];
roleIds: string[]; roleIds: string[];
posts: PostVO[]; posts: PostVO[];
postIds: string[]; postIds: string[];
roleGroup: string; roleGroup: string;
postGroup: string; postGroup: string;
} }
export interface ResetPwdForm { export interface ResetPwdForm {
oldPassword: string; oldPassword: string;
newPassword: string; newPassword: string;
confirmPassword: string; confirmPassword: string;
} }

View File

@ -4,84 +4,84 @@ import { AxiosPromise } from 'axios';
// 查询生成表数据 // 查询生成表数据
export const listTable = (query: TableQuery): AxiosPromise<TableVO[]> => { export const listTable = (query: TableQuery): AxiosPromise<TableVO[]> => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/list', url: '/tool/gen/list',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
// 查询db数据库列表 // 查询db数据库列表
export const listDbTable = (query: DbTableQuery): AxiosPromise<DbTableVO[]> => { export const listDbTable = (query: DbTableQuery): AxiosPromise<DbTableVO[]> => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/db/list', url: '/tool/gen/db/list',
method: 'get', method: 'get',
params: query params: query
}); });
}; };
// 查询表详细信息 // 查询表详细信息
export const getGenTable = (tableId: string | number): AxiosPromise<GenTableVO> => { export const getGenTable = (tableId: string | number): AxiosPromise<GenTableVO> => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/' + tableId, url: '/tool/gen/' + tableId,
method: 'get' method: 'get'
}); });
}; };
// 修改代码生成信息 // 修改代码生成信息
export const updateGenTable = (data: DbTableForm) => { export const updateGenTable = (data: DbTableForm) => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen', url: '/tool/gen',
method: 'put', method: 'put',
data: data data: data
}); });
}; };
// 导入表 // 导入表
export const importTable = (data: { tables: string }) => { export const importTable = (data: { tables: string }) => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/importTable', url: '/tool/gen/importTable',
method: 'post', method: 'post',
params: data params: data
}); });
}; };
// 预览生成代码 // 预览生成代码
export const previewTable = (tableId: string | number) => { export const previewTable = (tableId: string | number) => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/preview/' + tableId, url: '/tool/gen/preview/' + tableId,
method: 'get' method: 'get'
}); });
}; };
// 删除表数据 // 删除表数据
export const delTable = (tableId: string | number | Array<string | number>) => { export const delTable = (tableId: string | number | Array<string | number>) => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/' + tableId, url: '/tool/gen/' + tableId,
method: 'delete' method: 'delete'
}); });
}; };
// 生成代码(自定义路径) // 生成代码(自定义路径)
export const genCode = (tableName: string) => { export const genCode = (tableName: string) => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/genCode/' + tableName, url: '/tool/gen/genCode/' + tableName,
method: 'get' method: 'get'
}); });
}; };
// 同步数据库 // 同步数据库
export const synchDb = (tableName: string) => { export const synchDb = (tableName: string) => {
return request({ return request({
headers: { datasource: localStorage.getItem('dataName') }, headers: { datasource: localStorage.getItem('dataName') },
url: '/tool/gen/synchDb/' + tableName, url: '/tool/gen/synchDb/' + tableName,
method: 'get' method: 'get'
}); });
}; };

View File

@ -1,178 +1,178 @@
export interface TableVO extends BaseEntity { export interface TableVO extends BaseEntity {
createDept: number | string; createDept: number | string;
tableId: string | number; tableId: string | number;
tableName: string; tableName: string;
tableComment: string; tableComment: string;
subTableName?: any; subTableName?: any;
subTableFkName?: any; subTableFkName?: any;
className: string; className: string;
tplCategory: string; tplCategory: string;
packageName: string; packageName: string;
moduleName: string; moduleName: string;
businessName: string; businessName: string;
functionName: string; functionName: string;
functionAuthor: string; functionAuthor: string;
genType: string; genType: string;
genPath: string; genPath: string;
pkColumn?: any; pkColumn?: any;
columns?: any; columns?: any;
options?: any; options?: any;
remark?: any; remark?: any;
treeCode?: any; treeCode?: any;
treeParentCode?: any; treeParentCode?: any;
treeName?: any; treeName?: any;
menuIds?: any; menuIds?: any;
parentMenuId?: any; parentMenuId?: any;
parentMenuName?: any; parentMenuName?: any;
tree: boolean; tree: boolean;
crud: boolean; crud: boolean;
} }
export interface TableQuery extends PageQuery { export interface TableQuery extends PageQuery {
tableName: string; tableName: string;
tableComment: string; tableComment: string;
dataName: string; dataName: string;
} }
export interface DbColumnVO extends BaseEntity { export interface DbColumnVO extends BaseEntity {
createDept?: any; createDept?: any;
columnId?: any; columnId?: any;
tableId?: any; tableId?: any;
columnName?: any; columnName?: any;
columnComment?: any; columnComment?: any;
columnType?: any; columnType?: any;
javaType?: any; javaType?: any;
javaField?: any; javaField?: any;
isPk?: any; isPk?: any;
isIncrement?: any; isIncrement?: any;
isRequired?: any; isRequired?: any;
isInsert?: any; isInsert?: any;
isEdit?: any; isEdit?: any;
isList?: any; isList?: any;
isQuery?: any; isQuery?: any;
queryType?: any; queryType?: any;
htmlType?: any; htmlType?: any;
dictType?: any; dictType?: any;
sort?: any; sort?: any;
increment: boolean; increment: boolean;
capJavaField?: any; capJavaField?: any;
usableColumn: boolean; usableColumn: boolean;
superColumn: boolean; superColumn: boolean;
list: boolean; list: boolean;
pk: boolean; pk: boolean;
insert: boolean; insert: boolean;
edit: boolean; edit: boolean;
query: boolean; query: boolean;
required: boolean; required: boolean;
} }
export interface DbTableVO { export interface DbTableVO {
createDept?: any; createDept?: any;
tableId?: any; tableId?: any;
tableName: string; tableName: string;
tableComment: string; tableComment: string;
subTableName?: any; subTableName?: any;
subTableFkName?: any; subTableFkName?: any;
className?: any; className?: any;
tplCategory?: any; tplCategory?: any;
packageName?: any; packageName?: any;
moduleName?: any; moduleName?: any;
businessName?: any; businessName?: any;
functionName?: any; functionName?: any;
functionAuthor?: any; functionAuthor?: any;
genType?: any; genType?: any;
genPath?: any; genPath?: any;
pkColumn?: any; pkColumn?: any;
columns: DbColumnVO[]; columns: DbColumnVO[];
options?: any; options?: any;
remark?: any; remark?: any;
treeCode?: any; treeCode?: any;
treeParentCode?: any; treeParentCode?: any;
treeName?: any; treeName?: any;
menuIds?: any; menuIds?: any;
parentMenuId?: any; parentMenuId?: any;
parentMenuName?: any; parentMenuName?: any;
tree: boolean; tree: boolean;
crud: boolean; crud: boolean;
} }
export interface DbTableQuery extends PageQuery { export interface DbTableQuery extends PageQuery {
tableName: string; tableName: string;
tableComment: string; tableComment: string;
} }
export interface GenTableVO { export interface GenTableVO {
info: DbTableVO; info: DbTableVO;
rows: DbColumnVO[]; rows: DbColumnVO[];
tables: DbTableVO[]; tables: DbTableVO[];
} }
export interface DbColumnForm extends BaseEntity { export interface DbColumnForm extends BaseEntity {
createDept: number; createDept: number;
columnId: string; columnId: string;
tableId: string; tableId: string;
columnName: string; columnName: string;
columnComment: string; columnComment: string;
columnType: string; columnType: string;
javaType: string; javaType: string;
javaField: string; javaField: string;
isPk: string; isPk: string;
isIncrement: string; isIncrement: string;
isRequired: string; isRequired: string;
isInsert?: any; isInsert?: any;
isEdit: string; isEdit: string;
isList: string; isList: string;
isQuery?: any; isQuery?: any;
queryType: string; queryType: string;
htmlType: string; htmlType: string;
dictType: string; dictType: string;
sort: number; sort: number;
increment: boolean; increment: boolean;
capJavaField: string; capJavaField: string;
usableColumn: boolean; usableColumn: boolean;
superColumn: boolean; superColumn: boolean;
list: boolean; list: boolean;
pk: boolean; pk: boolean;
insert: boolean; insert: boolean;
edit: boolean; edit: boolean;
query: boolean; query: boolean;
required: boolean; required: boolean;
} }
export interface DbParamForm { export interface DbParamForm {
treeCode?: any; treeCode?: any;
treeName?: any; treeName?: any;
treeParentCode?: any; treeParentCode?: any;
parentMenuId: string; parentMenuId: string;
} }
export interface DbTableForm extends BaseEntity { export interface DbTableForm extends BaseEntity {
createDept?: any; createDept?: any;
tableId: string | string; tableId: string | string;
tableName: string; tableName: string;
tableComment: string; tableComment: string;
subTableName?: any; subTableName?: any;
subTableFkName?: any; subTableFkName?: any;
className: string; className: string;
tplCategory: string; tplCategory: string;
packageName: string; packageName: string;
moduleName: string; moduleName: string;
businessName: string; businessName: string;
functionName: string; functionName: string;
functionAuthor: string; functionAuthor: string;
genType: string; genType: string;
genPath: string; genPath: string;
pkColumn?: any; pkColumn?: any;
columns: DbColumnForm[]; columns: DbColumnForm[];
options: string; options: string;
remark?: any; remark?: any;
treeCode?: any; treeCode?: any;
treeParentCode?: any; treeParentCode?: any;
treeName?: any; treeName?: any;
menuIds?: any; menuIds?: any;
parentMenuId: string; parentMenuId: string;
parentMenuName?: any; parentMenuName?: any;
tree: boolean; tree: boolean;
crud: boolean; crud: boolean;
params: DbParamForm; params: DbParamForm;
} }

View File

@ -2,53 +2,53 @@
* 注册 * 注册
*/ */
export type RegisterForm = { export type RegisterForm = {
tenantId: string; tenantId: string;
username: string; username: string;
password: string; password: string;
confirmPassword?: string; confirmPassword?: string;
code?: string; code?: string;
uuid?: string; uuid?: string;
userType?: string; userType?: string;
}; };
/** /**
* 登录请求 * 登录请求
*/ */
export interface LoginData { export interface LoginData {
tenantId: string; tenantId: string;
username: string; username: string;
password: string; password: string;
rememberMe?: boolean; rememberMe?: boolean;
code?: string; code?: string;
uuid?: string; uuid?: string;
} }
/** /**
* 登录响应 * 登录响应
*/ */
export interface LoginResult { export interface LoginResult {
token: string; token: string;
} }
/** /**
* 验证码返回 * 验证码返回
*/ */
export interface VerifyCodeResult { export interface VerifyCodeResult {
captchaEnabled: boolean; captchaEnabled: boolean;
uuid?: string; uuid?: string;
img?: string; img?: string;
} }
/** /**
* 租户 * 租户
*/ */
export interface TenantVO { export interface TenantVO {
companyName: string; companyName: string;
domain: any; domain: any;
tenantId: string; tenantId: string;
} }
export interface TenantInfo { export interface TenantInfo {
tenantEnabled: boolean; tenantEnabled: boolean;
voList: TenantVO[]; voList: TenantVO[];
} }

View File

@ -1,99 +1,99 @@
@import './variables.module.scss'; @import './variables.module.scss';
@mixin colorBtn($color) { @mixin colorBtn($color) {
background: $color; background: $color;
&:hover { &:hover {
color: $color; color: $color;
&:before, &:before,
&:after { &:after {
background: $color; background: $color;
} }
} }
} }
.blue-btn { .blue-btn {
@include colorBtn($blue); @include colorBtn($blue);
} }
.light-blue-btn { .light-blue-btn {
@include colorBtn($light-blue); @include colorBtn($light-blue);
} }
.red-btn { .red-btn {
@include colorBtn($red); @include colorBtn($red);
} }
.pink-btn { .pink-btn {
@include colorBtn($pink); @include colorBtn($pink);
} }
.green-btn { .green-btn {
@include colorBtn($green); @include colorBtn($green);
} }
.tiffany-btn { .tiffany-btn {
@include colorBtn($tiffany); @include colorBtn($tiffany);
} }
.yellow-btn { .yellow-btn {
@include colorBtn($yellow); @include colorBtn($yellow);
} }
.pan-btn { .pan-btn {
font-size: 14px; font-size: 14px;
color: #fff; color: #fff;
padding: 14px 36px; padding: 14px 36px;
border-radius: 8px; border-radius: 8px;
border: none; border: none;
outline: none; outline: none;
transition: 600ms ease all; transition: 600ms ease all;
position: relative; position: relative;
display: inline-block; display: inline-block;
&:hover { &:hover {
background: #fff; background: #fff;
&:before, &:before,
&:after { &:after {
width: 100%; width: 100%;
transition: 600ms ease all; transition: 600ms ease all;
} }
} }
&:before, &:before,
&:after { &:after {
content: ''; content: '';
position: absolute; position: absolute;
top: 0; top: 0;
right: 0; right: 0;
height: 2px; height: 2px;
width: 0; width: 0;
transition: 400ms ease all; transition: 400ms ease all;
} }
&::after { &::after {
right: inherit; right: inherit;
top: inherit; top: inherit;
left: 0; left: 0;
bottom: 0; bottom: 0;
} }
} }
.custom-button { .custom-button {
display: inline-block; display: inline-block;
line-height: 1; line-height: 1;
white-space: nowrap; white-space: nowrap;
cursor: pointer; cursor: pointer;
background: #fff; background: #fff;
color: #fff; color: #fff;
-webkit-appearance: none; -webkit-appearance: none;
text-align: center; text-align: center;
box-sizing: border-box; box-sizing: border-box;
outline: 0; outline: 0;
margin: 0; margin: 0;
padding: 10px 15px; padding: 10px 15px;
font-size: 14px; font-size: 14px;
border-radius: 4px; border-radius: 4px;
} }

View File

@ -1,97 +1,97 @@
// cover some element-ui styles // cover some element-ui styles
.el-divider--horizontal { .el-divider--horizontal {
margin-bottom: 10px; margin-bottom: 10px;
margin-top: 10px; margin-top: 10px;
} }
.el-breadcrumb__inner, .el-breadcrumb__inner,
.el-breadcrumb__inner a { .el-breadcrumb__inner a {
font-weight: 400 !important; font-weight: 400 !important;
} }
.el-upload { .el-upload {
input[type='file'] { input[type='file'] {
display: none !important; display: none !important;
} }
} }
.el-upload__input { .el-upload__input {
display: none; display: none;
} }
.cell { .cell {
.el-tag { .el-tag {
margin-right: 0px; margin-right: 0px;
} }
} }
.small-padding { .small-padding {
.cell { .cell {
padding-left: 5px; padding-left: 5px;
padding-right: 5px; padding-right: 5px;
} }
} }
.fixed-width { .fixed-width {
.el-button--mini { .el-button--mini {
padding: 7px 10px; padding: 7px 10px;
width: 60px; width: 60px;
} }
} }
.status-col { .status-col {
.cell { .cell {
padding: 0 10px; padding: 0 10px;
text-align: center; text-align: center;
.el-tag { .el-tag {
margin-right: 0px; margin-right: 0px;
} }
} }
} }
// to fixed https://github.com/ElemeFE/element/issues/2461 // to fixed https://github.com/ElemeFE/element/issues/2461
.el-dialog { .el-dialog {
transform: none; transform: none;
left: 0; left: 0;
position: relative; position: relative;
margin: 0 auto; margin: 0 auto;
} }
// refine element ui upload // refine element ui upload
.upload-container { .upload-container {
.el-upload { .el-upload {
width: 100%; width: 100%;
.el-upload-dragger { .el-upload-dragger {
width: 100%; width: 100%;
height: 200px; height: 200px;
} }
} }
} }
// dropdown // dropdown
.el-dropdown-menu { .el-dropdown-menu {
a { a {
display: block; display: block;
} }
} }
// fix date-picker ui bug in filter-item // fix date-picker ui bug in filter-item
.el-range-editor.el-input__inner { .el-range-editor.el-input__inner {
display: inline-flex !important; display: inline-flex !important;
} }
// to fix el-date-picker css style // to fix el-date-picker css style
.el-range-separator { .el-range-separator {
box-sizing: content-box; box-sizing: content-box;
} }
.el-menu--collapse>div>.el-submenu>.el-submenu__title .el-submenu__icon-arrow { .el-menu--collapse>div>.el-submenu>.el-submenu__title .el-submenu__icon-arrow {
display: none; display: none;
} }
.el-dropdown .el-dropdown-link { .el-dropdown .el-dropdown-link {
color: var(--el-color-primary) !important; color: var(--el-color-primary) !important;
} }

View File

@ -9,201 +9,201 @@
@import 'element-plus/dist/index.css'; @import 'element-plus/dist/index.css';
body { body {
height: 100%; height: 100%;
margin: 0; margin: 0;
-moz-osx-font-smoothing: grayscale; -moz-osx-font-smoothing: grayscale;
-webkit-font-smoothing: antialiased; -webkit-font-smoothing: antialiased;
text-rendering: optimizeLegibility; text-rendering: optimizeLegibility;
font-family: Helvetica Neue, Helvetica, PingFang SC, Hiragino Sans GB, Microsoft YaHei, Arial, sans-serif; font-family: Helvetica Neue, Helvetica, PingFang SC, Hiragino Sans GB, Microsoft YaHei, Arial, sans-serif;
} }
label { label {
font-weight: 700; font-weight: 700;
} }
html { html {
height: 100%; height: 100%;
box-sizing: border-box; box-sizing: border-box;
} }
#app { #app {
height: 100%; height: 100%;
} }
*, *,
*:before, *:before,
*:after { *:after {
box-sizing: inherit; box-sizing: inherit;
} }
.no-padding { .no-padding {
padding: 0px !important; padding: 0px !important;
} }
.padding-content { .padding-content {
padding: 4px 0; padding: 4px 0;
} }
a:focus, a:focus,
a:active { a:active {
outline: none; outline: none;
} }
a, a,
a:focus, a:focus,
a:hover { a:hover {
cursor: pointer; cursor: pointer;
color: inherit; color: inherit;
text-decoration: none; text-decoration: none;
} }
div:focus { div:focus {
outline: none; outline: none;
} }
.fr { .fr {
float: right; float: right;
} }
.fl { .fl {
float: left; float: left;
} }
.pr-5 { .pr-5 {
padding-right: 5px; padding-right: 5px;
} }
.pl-5 { .pl-5 {
padding-left: 5px; padding-left: 5px;
} }
.block { .block {
display: block; display: block;
} }
.pointer { .pointer {
cursor: pointer; cursor: pointer;
} }
.inlineBlock { .inlineBlock {
display: block; display: block;
} }
.clearfix { .clearfix {
&:after { &:after {
visibility: hidden; visibility: hidden;
display: block; display: block;
font-size: 0; font-size: 0;
content: ' '; content: ' ';
clear: both; clear: both;
height: 0; height: 0;
} }
} }
aside { aside {
background: #eef1f6; background: #eef1f6;
padding: 8px 24px; padding: 8px 24px;
margin-bottom: 20px; margin-bottom: 20px;
border-radius: 2px; border-radius: 2px;
display: block; display: block;
line-height: 32px; line-height: 32px;
font-size: 16px; font-size: 16px;
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell, 'Fira Sans', 'Droid Sans', 'Helvetica Neue', font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell, 'Fira Sans', 'Droid Sans', 'Helvetica Neue',
sans-serif; sans-serif;
color: #2c3e50; color: #2c3e50;
-webkit-font-smoothing: antialiased; -webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale; -moz-osx-font-smoothing: grayscale;
a { a {
color: #337ab7; color: #337ab7;
cursor: pointer; cursor: pointer;
&:hover { &:hover {
color: rgb(32, 160, 255); color: rgb(32, 160, 255);
} }
} }
} }
//main-container全局样式 //main-container全局样式
.app-container { .app-container {
padding: 20px; padding: 20px;
} }
// search面板样式 // search面板样式
.panel, .panel,
.search { .search {
margin-bottom: 0.75rem; margin-bottom: 0.75rem;
border-radius: 0.25rem; border-radius: 0.25rem;
border: 1px solid var(--el-border-color-light); border: 1px solid var(--el-border-color-light);
background-color: var(--el-bg-color-overlay); background-color: var(--el-bg-color-overlay);
padding: 0.75rem; padding: 0.75rem;
--tw-shadow: var(--el-box-shadow-light); --tw-shadow: var(--el-box-shadow-light);
--tw-shadow-colored: var(--el-box-shadow-light); --tw-shadow-colored: var(--el-box-shadow-light);
box-shadow: var(--tw-ring-offset-shadow, 0 0 #0000), var(--tw-ring-shadow, 0 0 #0000), var(--tw-shadow); box-shadow: var(--tw-ring-offset-shadow, 0 0 #0000), var(--tw-ring-shadow, 0 0 #0000), var(--tw-shadow);
} }
.components-container { .components-container {
margin: 30px 50px; margin: 30px 50px;
position: relative; position: relative;
} }
.pagination-container { .pagination-container {
margin-top: 30px; margin-top: 30px;
} }
.text-center { .text-center {
text-align: center; text-align: center;
} }
.sub-navbar { .sub-navbar {
height: 50px; height: 50px;
line-height: 50px; line-height: 50px;
position: relative; position: relative;
width: 100%; width: 100%;
text-align: right; text-align: right;
padding-right: 20px; padding-right: 20px;
transition: 600ms ease position; transition: 600ms ease position;
background: linear-gradient(90deg, rgba(32, 182, 249, 1) 0%, rgba(32, 182, 249, 1) 0%, rgba(33, 120, 241, 1) 100%, rgba(33, 120, 241, 1) 100%); background: linear-gradient(90deg, rgba(32, 182, 249, 1) 0%, rgba(32, 182, 249, 1) 0%, rgba(33, 120, 241, 1) 100%, rgba(33, 120, 241, 1) 100%);
.subtitle { .subtitle {
font-size: 20px; font-size: 20px;
color: #fff; color: #fff;
} }
&.draft { &.draft {
background: #d0d0d0; background: #d0d0d0;
} }
&.deleted { &.deleted {
background: #d0d0d0; background: #d0d0d0;
} }
} }
.link-type, .link-type,
.link-type:focus { .link-type:focus {
color: #337ab7; color: #337ab7;
cursor: pointer; cursor: pointer;
&:hover { &:hover {
color: rgb(32, 160, 255); color: rgb(32, 160, 255);
} }
} }
.filter-container { .filter-container {
padding-bottom: 10px; padding-bottom: 10px;
.filter-item { .filter-item {
display: inline-block; display: inline-block;
vertical-align: middle; vertical-align: middle;
margin-bottom: 10px; margin-bottom: 10px;
} }
} }
//refine vue-multiselect plugin //refine vue-multiselect plugin
.multiselect { .multiselect {
line-height: 16px; line-height: 16px;
} }
.multiselect--active { .multiselect--active {
z-index: 1000 !important; z-index: 1000 !important;
} }

View File

@ -1,60 +1,60 @@
@mixin clearfix { @mixin clearfix {
&:after { &:after {
content: ''; content: '';
display: table; display: table;
clear: both; clear: both;
} }
} }
@mixin scrollBar { @mixin scrollBar {
&::-webkit-scrollbar-track-piece { &::-webkit-scrollbar-track-piece {
background: #d3dce6; background: #d3dce6;
} }
&::-webkit-scrollbar { &::-webkit-scrollbar {
width: 6px; width: 6px;
} }
&::-webkit-scrollbar-thumb { &::-webkit-scrollbar-thumb {
background: #99a9bf; background: #99a9bf;
border-radius: 20px; border-radius: 20px;
} }
} }
@mixin relative { @mixin relative {
position: relative; position: relative;
width: 100%; width: 100%;
height: 100%; height: 100%;
} }
@mixin pct($pct) { @mixin pct($pct) {
width: #{$pct}; width: #{$pct};
position: relative; position: relative;
margin: 0 auto; margin: 0 auto;
} }
@mixin triangle($width, $height, $color, $direction) { @mixin triangle($width, $height, $color, $direction) {
$width: $width/2; $width: $width/2;
$color-border-style: $height solid $color; $color-border-style: $height solid $color;
$transparent-border-style: $width solid transparent; $transparent-border-style: $width solid transparent;
height: 0; height: 0;
width: 0; width: 0;
@if $direction==up { @if $direction==up {
border-bottom: $color-border-style; border-bottom: $color-border-style;
border-left: $transparent-border-style; border-left: $transparent-border-style;
border-right: $transparent-border-style; border-right: $transparent-border-style;
} @else if $direction==right { } @else if $direction==right {
border-left: $color-border-style; border-left: $color-border-style;
border-top: $transparent-border-style; border-top: $transparent-border-style;
border-bottom: $transparent-border-style; border-bottom: $transparent-border-style;
} @else if $direction==down { } @else if $direction==down {
border-top: $color-border-style; border-top: $color-border-style;
border-left: $transparent-border-style; border-left: $transparent-border-style;
border-right: $transparent-border-style; border-right: $transparent-border-style;
} @else if $direction==left { } @else if $direction==left {
border-right: $color-border-style; border-right: $color-border-style;
border-top: $transparent-border-style; border-top: $transparent-border-style;
border-bottom: $transparent-border-style; border-bottom: $transparent-border-style;
} }
} }

View File

@ -5,52 +5,52 @@
/** 基础通用 **/ /** 基础通用 **/
.pt5 { .pt5 {
padding-top: 5px; padding-top: 5px;
} }
.pr5 { .pr5 {
padding-right: 5px; padding-right: 5px;
} }
.pb5 { .pb5 {
padding-bottom: 5px; padding-bottom: 5px;
} }
.mt5 { .mt5 {
margin-top: 5px; margin-top: 5px;
} }
.mr5 { .mr5 {
margin-right: 5px; margin-right: 5px;
} }
.mb5 { .mb5 {
margin-bottom: 5px; margin-bottom: 5px;
} }
.mb8 { .mb8 {
margin-bottom: 8px; margin-bottom: 8px;
} }
.ml5 { .ml5 {
margin-left: 5px; margin-left: 5px;
} }
.mt10 { .mt10 {
margin-top: 10px; margin-top: 10px;
} }
.mr10 { .mr10 {
margin-right: 10px; margin-right: 10px;
} }
.mb10 { .mb10 {
margin-bottom: 10px; margin-bottom: 10px;
} }
.ml10 { .ml10 {
margin-left: 10px; margin-left: 10px;
} }
.mt20 { .mt20 {
margin-top: 20px; margin-top: 20px;
} }
.mr20 { .mr20 {
margin-right: 20px; margin-right: 20px;
} }
.mb20 { .mb20 {
margin-bottom: 20px; margin-bottom: 20px;
} }
.ml20 { .ml20 {
margin-left: 20px; margin-left: 20px;
} }
.h1, .h1,
@ -65,226 +65,226 @@ h3,
h4, h4,
h5, h5,
h6 { h6 {
font-family: inherit; font-family: inherit;
font-weight: 500; font-weight: 500;
line-height: 1.1; line-height: 1.1;
color: inherit; color: inherit;
} }
.el-form .el-form-item__label { .el-form .el-form-item__label {
font-weight: 700; font-weight: 700;
} }
.el-dialog:not(.is-fullscreen) { .el-dialog:not(.is-fullscreen) {
margin-top: 6vh !important; margin-top: 6vh !important;
} }
.el-dialog.scrollbar .el-dialog__body { .el-dialog.scrollbar .el-dialog__body {
overflow: auto; overflow: auto;
overflow-x: hidden; overflow-x: hidden;
max-height: 70vh; max-height: 70vh;
padding: 10px 20px 0; padding: 10px 20px 0;
} }
.el-table { .el-table {
.el-table__header-wrapper, .el-table__header-wrapper,
.el-table__fixed-header-wrapper { .el-table__fixed-header-wrapper {
th { th {
word-break: break-word; word-break: break-word;
background-color: #f8f8f9 !important; background-color: #f8f8f9 !important;
color: #515a6e; color: #515a6e;
height: 40px !important; height: 40px !important;
font-size: 13px; font-size: 13px;
} }
} }
.el-table__body-wrapper { .el-table__body-wrapper {
.el-button [class*='el-icon-'] + span { .el-button [class*='el-icon-'] + span {
margin-left: 1px; margin-left: 1px;
} }
} }
} }
/** 表单布局 **/ /** 表单布局 **/
.form-header { .form-header {
font-size: 15px; font-size: 15px;
color: #6379bb; color: #6379bb;
border-bottom: 1px solid #ddd; border-bottom: 1px solid #ddd;
margin: 8px 10px 25px 10px; margin: 8px 10px 25px 10px;
padding-bottom: 5px; padding-bottom: 5px;
} }
/** 表格布局 **/ /** 表格布局 **/
.pagination-container { .pagination-container {
// position: relative; // position: relative;
height: 25px; height: 25px;
margin-bottom: 10px; margin-bottom: 10px;
margin-top: 15px; margin-top: 15px;
padding: 10px 20px !important; padding: 10px 20px !important;
} }
/* tree border */ /* tree border */
.tree-border { .tree-border {
margin-top: 5px; margin-top: 5px;
border: 1px solid #e5e6e7; border: 1px solid #e5e6e7;
background: #ffffff none; background: #ffffff none;
border-radius: 4px; border-radius: 4px;
width: 100%; width: 100%;
} }
.pagination-container .el-pagination { .pagination-container .el-pagination {
//right: 0; //right: 0;
//position: absolute; //position: absolute;
} }
@media (max-width: 768px) { @media (max-width: 768px) {
.pagination-container .el-pagination > .el-pagination__jump { .pagination-container .el-pagination > .el-pagination__jump {
display: none !important; display: none !important;
} }
.pagination-container .el-pagination > .el-pagination__sizes { .pagination-container .el-pagination > .el-pagination__sizes {
display: none !important; display: none !important;
} }
} }
.el-table .fixed-width .el-button--small { .el-table .fixed-width .el-button--small {
padding-left: 0; padding-left: 0;
padding-right: 0; padding-right: 0;
width: inherit; width: inherit;
} }
/** 表格更多操作下拉样式 */ /** 表格更多操作下拉样式 */
.el-table .el-dropdown-link { .el-table .el-dropdown-link {
cursor: pointer; cursor: pointer;
color: #409eff; color: #409eff;
margin-left: 10px; margin-left: 10px;
} }
.el-table .el-dropdown, .el-table .el-dropdown,
.el-icon-arrow-down { .el-icon-arrow-down {
font-size: 12px; font-size: 12px;
} }
.el-tree-node__content > .el-checkbox { .el-tree-node__content > .el-checkbox {
margin-right: 8px; margin-right: 8px;
} }
.list-group-striped > .list-group-item { .list-group-striped > .list-group-item {
border-left: 0; border-left: 0;
border-right: 0; border-right: 0;
border-radius: 0; border-radius: 0;
padding-left: 0; padding-left: 0;
padding-right: 0; padding-right: 0;
} }
.list-group { .list-group {
padding-left: 0px; padding-left: 0px;
list-style: none; list-style: none;
} }
.list-group-item { .list-group-item {
border-bottom: 1px solid #e7eaec; border-bottom: 1px solid #e7eaec;
border-top: 1px solid #e7eaec; border-top: 1px solid #e7eaec;
margin-bottom: -1px; margin-bottom: -1px;
padding: 11px 0px; padding: 11px 0px;
font-size: 13px; font-size: 13px;
} }
.pull-right { .pull-right {
float: right !important; float: right !important;
} }
.el-card__header { .el-card__header {
padding: 14px 15px 7px !important; padding: 14px 15px 7px !important;
min-height: 40px; min-height: 40px;
} }
.el-card__body { .el-card__body {
padding: 15px 20px 20px 20px !important; padding: 15px 20px 20px 20px !important;
} }
.card-box { .card-box {
padding-right: 15px; padding-right: 15px;
padding-left: 15px; padding-left: 15px;
margin-bottom: 10px; margin-bottom: 10px;
} }
/* button color */ /* button color */
.el-button--cyan.is-active, .el-button--cyan.is-active,
.el-button--cyan:active { .el-button--cyan:active {
background: #20b2aa; background: #20b2aa;
border-color: #20b2aa; border-color: #20b2aa;
color: #ffffff; color: #ffffff;
} }
.el-button--cyan:focus, .el-button--cyan:focus,
.el-button--cyan:hover { .el-button--cyan:hover {
background: #48d1cc; background: #48d1cc;
border-color: #48d1cc; border-color: #48d1cc;
color: #ffffff; color: #ffffff;
} }
.el-button--cyan { .el-button--cyan {
background-color: #20b2aa; background-color: #20b2aa;
border-color: #20b2aa; border-color: #20b2aa;
color: #ffffff; color: #ffffff;
} }
/* text color */ /* text color */
.text-navy { .text-navy {
color: #1ab394; color: #1ab394;
} }
.text-primary { .text-primary {
color: inherit; color: inherit;
} }
.text-success { .text-success {
color: #1c84c6; color: #1c84c6;
} }
.text-info { .text-info {
color: #23c6c8; color: #23c6c8;
} }
.text-warning { .text-warning {
color: #f8ac59; color: #f8ac59;
} }
.text-danger { .text-danger {
color: #ed5565; color: #ed5565;
} }
.text-muted { .text-muted {
color: #888888; color: #888888;
} }
/* image */ /* image */
.img-circle { .img-circle {
border-radius: 50%; border-radius: 50%;
} }
.img-lg { .img-lg {
width: 120px; width: 120px;
height: 120px; height: 120px;
} }
.avatar-upload-preview { .avatar-upload-preview {
position: absolute; position: absolute;
top: 50%; top: 50%;
transform: translate(50%, -50%); transform: translate(50%, -50%);
width: 200px; width: 200px;
height: 200px; height: 200px;
border-radius: 50%; border-radius: 50%;
box-shadow: 0 0 4px #ccc; box-shadow: 0 0 4px #ccc;
overflow: hidden; overflow: hidden;
} }
/* 拖拽列样式 */ /* 拖拽列样式 */
.sortable-ghost { .sortable-ghost {
opacity: 0.8; opacity: 0.8;
color: #fff !important; color: #fff !important;
background: #42b983 !important; background: #42b983 !important;
} }
/* 表格右侧工具栏样式 */ /* 表格右侧工具栏样式 */
.top-right-btn { .top-right-btn {
margin-left: auto; margin-left: auto;
} }

View File

@ -1,236 +1,236 @@
#app { #app {
.main-container { .main-container {
min-height: 100%; min-height: 100%;
transition: margin-left 0.28s; transition: margin-left 0.28s;
margin-left: $base-sidebar-width; margin-left: $base-sidebar-width;
position: relative; position: relative;
} }
.sidebarHide { .sidebarHide {
margin-left: 0 !important; margin-left: 0 !important;
} }
.sidebar-container { .sidebar-container {
-webkit-transition: width 0.28s; -webkit-transition: width 0.28s;
transition: width 0.28s; transition: width 0.28s;
width: $base-sidebar-width !important; width: $base-sidebar-width !important;
background-color: $base-menu-background; background-color: $base-menu-background;
height: 100%; height: 100%;
position: fixed; position: fixed;
font-size: 0px; font-size: 0px;
top: 0; top: 0;
bottom: 0; bottom: 0;
left: 0; left: 0;
z-index: 1001; z-index: 1001;
overflow: hidden; overflow: hidden;
-webkit-box-shadow: 2px 0 6px rgba(0, 21, 41, 0.35); -webkit-box-shadow: 2px 0 6px rgba(0, 21, 41, 0.35);
box-shadow: 2px 0 6px rgba(0, 21, 41, 0.35); box-shadow: 2px 0 6px rgba(0, 21, 41, 0.35);
// reset element-ui css // reset element-ui css
.horizontal-collapse-transition { .horizontal-collapse-transition {
transition: 0s width ease-in-out, 0s padding-left ease-in-out, 0s padding-right ease-in-out; transition: 0s width ease-in-out, 0s padding-left ease-in-out, 0s padding-right ease-in-out;
} }
.scrollbar-wrapper { .scrollbar-wrapper {
overflow-x: hidden !important; overflow-x: hidden !important;
} }
.el-scrollbar__bar.is-vertical { .el-scrollbar__bar.is-vertical {
right: 0px; right: 0px;
} }
.el-scrollbar { .el-scrollbar {
height: 100%; height: 100%;
} }
&.has-logo { &.has-logo {
.el-scrollbar { .el-scrollbar {
height: calc(100% - 50px); height: calc(100% - 50px);
} }
} }
.is-horizontal { .is-horizontal {
display: none; display: none;
} }
a { a {
display: inline-block; display: inline-block;
width: 100%; width: 100%;
overflow: hidden; overflow: hidden;
} }
.svg-icon { .svg-icon {
margin-right: 16px; margin-right: 16px;
} }
.el-menu { .el-menu {
border: none; border: none;
height: 100%; height: 100%;
width: 100% !important; width: 100% !important;
} }
.el-menu-item, .el-menu-item,
.menu-title { .menu-title {
overflow: hidden !important; overflow: hidden !important;
text-overflow: ellipsis !important; text-overflow: ellipsis !important;
white-space: nowrap !important; white-space: nowrap !important;
} }
.el-menu-item .el-menu-tooltip__trigger { .el-menu-item .el-menu-tooltip__trigger {
display: inline-block !important; display: inline-block !important;
} }
// menu hover // menu hover
.sub-menu-title-noDropdown, .sub-menu-title-noDropdown,
.el-sub-menu__title { .el-sub-menu__title {
&:hover { &:hover {
background-color: rgba(0, 0, 0, 0.06) !important; background-color: rgba(0, 0, 0, 0.06) !important;
} }
} }
& .theme-dark .is-active > .el-sub-menu__title { & .theme-dark .is-active > .el-sub-menu__title {
color: $base-menu-color-active !important; color: $base-menu-color-active !important;
} }
& .nest-menu .el-sub-menu > .el-sub-menu__title, & .nest-menu .el-sub-menu > .el-sub-menu__title,
& .el-sub-menu .el-menu-item { & .el-sub-menu .el-menu-item {
min-width: $base-sidebar-width !important; min-width: $base-sidebar-width !important;
&:hover { &:hover {
background-color: rgba(0, 0, 0, 0.06) !important; background-color: rgba(0, 0, 0, 0.06) !important;
} }
} }
& .theme-dark .nest-menu .el-sub-menu > .el-sub-menu__title, & .theme-dark .nest-menu .el-sub-menu > .el-sub-menu__title,
& .theme-dark .el-sub-menu .el-menu-item { & .theme-dark .el-sub-menu .el-menu-item {
background-color: $base-sub-menu-background !important; background-color: $base-sub-menu-background !important;
&:hover { &:hover {
background-color: $base-sub-menu-hover !important; background-color: $base-sub-menu-hover !important;
} }
} }
} }
.hideSidebar { .hideSidebar {
.sidebar-container { .sidebar-container {
width: 54px !important; width: 54px !important;
} }
.main-container { .main-container {
margin-left: 54px; margin-left: 54px;
} }
.sub-menu-title-noDropdown { .sub-menu-title-noDropdown {
padding: 0 !important; padding: 0 !important;
position: relative; position: relative;
.el-tooltip { .el-tooltip {
padding: 0 !important; padding: 0 !important;
.svg-icon { .svg-icon {
margin-left: 20px; margin-left: 20px;
} }
} }
} }
.el-sub-menu { .el-sub-menu {
overflow: hidden; overflow: hidden;
& > .el-sub-menu__title { & > .el-sub-menu__title {
padding: 0 !important; padding: 0 !important;
.svg-icon { .svg-icon {
margin-left: 20px; margin-left: 20px;
} }
} }
} }
.el-menu--collapse { .el-menu--collapse {
.el-sub-menu { .el-sub-menu {
& > .el-sub-menu__title { & > .el-sub-menu__title {
& > span { & > span {
height: 0; height: 0;
width: 0; width: 0;
overflow: hidden; overflow: hidden;
visibility: hidden; visibility: hidden;
display: inline-block; display: inline-block;
} }
& > i { & > i {
height: 0; height: 0;
width: 0; width: 0;
overflow: hidden; overflow: hidden;
visibility: hidden; visibility: hidden;
display: inline-block; display: inline-block;
} }
} }
} }
} }
} }
.el-menu--collapse .el-menu .el-sub-menu { .el-menu--collapse .el-menu .el-sub-menu {
min-width: $base-sidebar-width !important; min-width: $base-sidebar-width !important;
} }
// mobile responsive // mobile responsive
.mobile { .mobile {
.main-container { .main-container {
margin-left: 0px; margin-left: 0px;
} }
.sidebar-container { .sidebar-container {
transition: transform 0.28s; transition: transform 0.28s;
width: $base-sidebar-width !important; width: $base-sidebar-width !important;
} }
&.hideSidebar { &.hideSidebar {
.sidebar-container { .sidebar-container {
pointer-events: none; pointer-events: none;
transition-duration: 0.3s; transition-duration: 0.3s;
transform: translate3d(-$base-sidebar-width, 0, 0); transform: translate3d(-$base-sidebar-width, 0, 0);
} }
} }
} }
.withoutAnimation { .withoutAnimation {
.main-container, .main-container,
.sidebar-container { .sidebar-container {
transition: none; transition: none;
} }
} }
} }
// when menu collapsed // when menu collapsed
.el-menu--vertical { .el-menu--vertical {
& > .el-menu { & > .el-menu {
.svg-icon { .svg-icon {
margin-right: 16px; margin-right: 16px;
} }
} }
.nest-menu .el-sub-menu > .el-sub-menu__title, .nest-menu .el-sub-menu > .el-sub-menu__title,
.el-menu-item { .el-menu-item {
&:hover { &:hover {
// you can use $sub-menuHover // you can use $sub-menuHover
background-color: rgba(0, 0, 0, 0.06) !important; background-color: rgba(0, 0, 0, 0.06) !important;
} }
} }
// the scroll bar appears when the sub-menu is too long // the scroll bar appears when the sub-menu is too long
> .el-menu--popup { > .el-menu--popup {
max-height: 100vh; max-height: 100vh;
overflow-y: auto; overflow-y: auto;
&::-webkit-scrollbar-track-piece { &::-webkit-scrollbar-track-piece {
background: #d3dce6; background: #d3dce6;
} }
&::-webkit-scrollbar { &::-webkit-scrollbar {
width: 6px; width: 6px;
} }
&::-webkit-scrollbar-thumb { &::-webkit-scrollbar-thumb {
background: #99a9bf; background: #99a9bf;
border-radius: 20px; border-radius: 20px;
} }
} }
} }

View File

@ -3,51 +3,51 @@
/* fade */ /* fade */
.fade-enter-active, .fade-enter-active,
.fade-leave-active { .fade-leave-active {
transition: opacity 0.28s; transition: opacity 0.28s;
} }
.fade-enter, .fade-enter,
.fade-leave-active { .fade-leave-active {
opacity: 0; opacity: 0;
} }
/* fade-transform */ /* fade-transform */
.fade-transform--move, .fade-transform--move,
.fade-transform-leave-active, .fade-transform-leave-active,
.fade-transform-enter-active { .fade-transform-enter-active {
transition: all 0.5s; transition: all 0.5s;
} }
.fade-transform-leave-active { .fade-transform-leave-active {
position: absolute; position: absolute;
} }
.fade-transform-enter { .fade-transform-enter {
opacity: 0; opacity: 0;
transform: translateX(-30px); transform: translateX(-30px);
} }
.fade-transform-leave-to { .fade-transform-leave-to {
opacity: 0; opacity: 0;
transform: translateX(30px); transform: translateX(30px);
} }
/* breadcrumb transition */ /* breadcrumb transition */
.breadcrumb-enter-active, .breadcrumb-enter-active,
.breadcrumb-leave-active { .breadcrumb-leave-active {
transition: all 0.5s; transition: all 0.5s;
} }
.breadcrumb-enter, .breadcrumb-enter,
.breadcrumb-leave-active { .breadcrumb-leave-active {
opacity: 0; opacity: 0;
transform: translateX(20px); transform: translateX(20px);
} }
.breadcrumb-move { .breadcrumb-move {
transition: all 0.5s; transition: all 0.5s;
} }
.breadcrumb-leave-active { .breadcrumb-leave-active {
position: absolute; position: absolute;
} }

View File

@ -47,19 +47,19 @@ $base-sidebar-width: 200px;
// the :export directive is the magic sauce for webpack // the :export directive is the magic sauce for webpack
// https://www.bluematador.com/blog/how-to-share-variables-between-js-and-sass // https://www.bluematador.com/blog/how-to-share-variables-between-js-and-sass
:export { :export {
menuColor: $base-menu-color; menuColor: $base-menu-color;
menuLightColor: $base-menu-light-color; menuLightColor: $base-menu-light-color;
menuColorActive: $base-menu-color-active; menuColorActive: $base-menu-color-active;
menuBackground: $base-menu-background; menuBackground: $base-menu-background;
menuLightBackground: $base-menu-light-background; menuLightBackground: $base-menu-light-background;
subMenuBackground: $base-sub-menu-background; subMenuBackground: $base-sub-menu-background;
subMenuHover: $base-sub-menu-hover; subMenuHover: $base-sub-menu-hover;
sideBarWidth: $base-sidebar-width; sideBarWidth: $base-sidebar-width;
logoTitleColor: $base-logo-title-color; logoTitleColor: $base-logo-title-color;
logoLightTitleColor: $base-logo-light-title-color; logoLightTitleColor: $base-logo-light-title-color;
primaryColor: $--color-primary; primaryColor: $--color-primary;
successColor: $--color-success; successColor: $--color-success;
dangerColor: $--color-danger; dangerColor: $--color-danger;
infoColor: $--color-info; infoColor: $--color-info;
warningColor: $--color-warning; warningColor: $--color-warning;
} }

View File

@ -1,3 +1,15 @@
<template>
<el-breadcrumb class="app-breadcrumb" separator="/">
<transition-group name="breadcrumb">
<el-breadcrumb-item v-for="(item, index) in levelList" :key="item.path">
<span v-if="item.redirect === 'noRedirect' || index == levelList.length - 1" class="no-redirect">{{
item.meta?.title }}</span>
<a v-else @click.prevent="handleLink(item)">{{ item.meta?.title }}</a>
</el-breadcrumb-item>
</transition-group>
</el-breadcrumb>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { RouteLocationMatched } from 'vue-router' import { RouteLocationMatched } from 'vue-router'
@ -6,49 +18,37 @@ const router = useRouter();
const levelList = ref<RouteLocationMatched[]>([]) const levelList = ref<RouteLocationMatched[]>([])
const getBreadcrumb = () => { const getBreadcrumb = () => {
// only show routes with meta.title // only show routes with meta.title
let matched = route.matched.filter(item => item.meta && item.meta.title); let matched = route.matched.filter(item => item.meta && item.meta.title);
const first = matched[0] const first = matched[0]
// 判断是否为首页 // 判断是否为首页
if (!isDashboard(first)) { if (!isDashboard(first)) {
matched = ([{ path: '/index', meta: { title: '首页' } }] as any).concat(matched) matched = ([{ path: '/index', meta: { title: '首页' } }] as any).concat(matched)
} }
levelList.value = matched.filter(item => item.meta && item.meta.title && item.meta.breadcrumb !== false) levelList.value = matched.filter(item => item.meta && item.meta.title && item.meta.breadcrumb !== false)
} }
const isDashboard = (route: RouteLocationMatched) => { const isDashboard = (route: RouteLocationMatched) => {
const name = route && route.name as string const name = route && route.name as string
if (!name) { if (!name) {
return false return false
} }
return name.trim() === 'Index' return name.trim() === 'Index'
} }
const handleLink = (item: RouteLocationMatched) => { const handleLink = (item: RouteLocationMatched) => {
const { redirect, path } = item const { redirect, path } = item
redirect ? router.push(redirect as string) : router.push(path) redirect ? router.push(redirect as string) : router.push(path)
} }
watchEffect(() => { watchEffect(() => {
// if you go to the redirect page, do not update the breadcrumbs // if you go to the redirect page, do not update the breadcrumbs
if (route.path.startsWith('/redirect/')) return if (route.path.startsWith('/redirect/')) return
getBreadcrumb() getBreadcrumb()
}) })
onMounted(() => { onMounted(() => {
getBreadcrumb(); getBreadcrumb();
}) })
</script> </script>
<template>
<el-breadcrumb class="app-breadcrumb" separator="/">
<transition-group name="breadcrumb">
<el-breadcrumb-item v-for="(item, index) in levelList" :key="item.path">
<span v-if="item.redirect === 'noRedirect' || index == levelList.length - 1" class="no-redirect">{{
item.meta?.title }}</span>
<a v-else @click.prevent="handleLink(item)">{{ item.meta?.title }}</a>
</el-breadcrumb-item>
</transition-group>
</el-breadcrumb>
</template>
<style lang="scss" scoped> <style lang="scss" scoped>
.app-breadcrumb.el-breadcrumb { .app-breadcrumb.el-breadcrumb {
display: inline-block; display: inline-block;

View File

@ -1,50 +1,50 @@
<template>
<div>
<template v-for="(item, index) in options">
<template v-if="values.includes(item.value)">
<span
v-if="item.elTagType == 'default' || item.elTagType == ''"
:key="item.value"
:index="index"
:class="item.elTagClass"
>{{ item.label }}</span
>
<el-tag
v-else
:disable-transitions="true"
:key="item.value + ''"
:index="index"
:type="item.elTagType === 'primary' ? '' : item.elTagType"
:class="item.elTagClass"
>{{ item.label }}</el-tag
>
</template>
</template>
</div>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { PropType } from 'vue'; import { PropType } from 'vue';
const props = defineProps({ const props = defineProps({
// 数据 // 数据
options: { options: {
type: Array as PropType<DictDataOption[]>, type: Array as PropType<DictDataOption[]>,
default: null, default: null,
}, },
// 当前的值 // 当前的值
value: [Number, String, Array], value: [Number, String, Array],
}) })
const values = computed(() => { const values = computed(() => {
if (props.value !== null && typeof props.value !== 'undefined') { if (props.value !== null && typeof props.value !== 'undefined') {
return Array.isArray(props.value) ? props.value : [String(props.value)]; return Array.isArray(props.value) ? props.value : [String(props.value)];
} else { } else {
return []; return [];
} }
}) })
</script> </script>
<template>
<div>
<template v-for="(item, index) in options">
<template v-if="values.includes(item.value)">
<span
v-if="item.elTagType == 'default' || item.elTagType == ''"
:key="item.value"
:index="index"
:class="item.elTagClass"
>{{ item.label }}</span
>
<el-tag
v-else
:disable-transitions="true"
:key="item.value + ''"
:index="index"
:type="item.elTagType === 'primary' ? '' : item.elTagType"
:class="item.elTagClass"
>{{ item.label }}</el-tag
>
</template>
</template>
</div>
</template>
<style scoped> <style scoped>
.el-tag + .el-tag { .el-tag + .el-tag {
margin-left: 10px; margin-left: 10px;

View File

@ -1,3 +1,31 @@
<template>
<div>
<el-upload
:action="upload.url"
:before-upload="handleBeforeUpload"
:on-success="handleUploadSuccess"
:on-error="handleUploadError"
class="editor-img-uploader"
name="file"
:show-file-list="false"
:headers="upload.headers"
style="display: none"
v-if="type === 'url'"
>
</el-upload>
<div class="editor">
<quill-editor
ref="myQuillEditor"
v-model:content="content"
contentType="html"
@textChange="(e: any) => $emit('update:modelValue', content)"
:options="options"
:style="styles"
/>
</div>
</div>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { QuillEditor, Quill } from '@vueup/vue-quill'; import { QuillEditor, Quill } from '@vueup/vue-quill';
import '@vueup/vue-quill/dist/vue-quill.snow.css'; import '@vueup/vue-quill/dist/vue-quill.snow.css';
@ -5,166 +33,138 @@ import { getToken } from "@/utils/auth";
import { ComponentInternalInstance } from "vue"; import { ComponentInternalInstance } from "vue";
const props = defineProps({ const props = defineProps({
/* 编辑器的内容 */ /* 编辑器的内容 */
modelValue: { modelValue: {
type: String, type: String,
}, },
/* 高度 */ /* 高度 */
height: { height: {
type: Number, type: Number,
default: null, default: null,
}, },
/* 最小高度 */ /* 最小高度 */
minHeight: { minHeight: {
type: Number, type: Number,
default: null, default: null,
}, },
/* 只读 */ /* 只读 */
readOnly: { readOnly: {
type: Boolean, type: Boolean,
default: false, default: false,
}, },
/* 上传文件大小限制(MB) */ /* 上传文件大小限制(MB) */
fileSize: { fileSize: {
type: Number, type: Number,
default: 5, default: 5,
}, },
/* 类型base64格式、url格式 */ /* 类型base64格式、url格式 */
type: { type: {
type: String, type: String,
default: "url", default: "url",
} }
}); });
const { proxy } = getCurrentInstance() as ComponentInternalInstance; const { proxy } = getCurrentInstance() as ComponentInternalInstance;
const upload = reactive<UploadOption>({ const upload = reactive<UploadOption>({
headers: { Authorization: "Bearer " + getToken() }, headers: { Authorization: "Bearer " + getToken() },
url: import.meta.env.VITE_APP_BASE_API + '/system/oss/upload' url: import.meta.env.VITE_APP_BASE_API + '/system/oss/upload'
}) })
const myQuillEditor = ref(); const myQuillEditor = ref();
const options = ref({ const options = ref({
theme: "snow", theme: "snow",
bounds: document.body, bounds: document.body,
debug: "warn", debug: "warn",
modules: { modules: {
// 工具栏配置 // 工具栏配置
toolbar: { toolbar: {
container: [ container: [
["bold", "italic", "underline", "strike"], // 加粗 斜体 下划线 删除线 ["bold", "italic", "underline", "strike"], // 加粗 斜体 下划线 删除线
["blockquote", "code-block"], // 引用 代码块 ["blockquote", "code-block"], // 引用 代码块
[{ list: "ordered" }, { list: "bullet"} ], // 有序、无序列表 [{ list: "ordered" }, { list: "bullet"} ], // 有序、无序列表
[{ indent: "-1" }, { indent: "+1" }], // 缩进 [{ indent: "-1" }, { indent: "+1" }], // 缩进
[{ size: ["small", false, "large", "huge"] }], // 字体大小 [{ size: ["small", false, "large", "huge"] }], // 字体大小
[{ header: [1, 2, 3, 4, 5, 6, false] }], // 标题 [{ header: [1, 2, 3, 4, 5, 6, false] }], // 标题
[{ color: [] }, { background: [] }], // 字体颜色、字体背景颜色 [{ color: [] }, { background: [] }], // 字体颜色、字体背景颜色
[{ align: [] }], // 对齐方式 [{ align: [] }], // 对齐方式
["clean"], // 清除文本格式 ["clean"], // 清除文本格式
["link", "image", "video"] // 链接、图片、视频 ["link", "image", "video"] // 链接、图片、视频
], ],
handlers: { handlers: {
image: function (value: any) { image: function (value: any) {
if (value) { if (value) {
// 调用element图片上传 // 调用element图片上传
(document.querySelector(".editor-img-uploader>.el-upload") as HTMLDivElement)?.click(); (document.querySelector(".editor-img-uploader>.el-upload") as HTMLDivElement)?.click();
} else { } else {
Quill.format("image", true); Quill.format("image", true);
} }
}, },
}, },
} }
}, },
placeholder: '请输入内容', placeholder: '请输入内容',
readOnly: props.readOnly, readOnly: props.readOnly,
}); });
const styles = computed(() => { const styles = computed(() => {
let style: any = {}; let style: any = {};
if (props.minHeight) { if (props.minHeight) {
style.minHeight = `${props.minHeight}px`; style.minHeight = `${props.minHeight}px`;
} }
if (props.height) { if (props.height) {
style.height = `${props.height}px`; style.height = `${props.height}px`;
} }
return style; return style;
}) })
const content = ref(""); const content = ref("");
watch(() => props.modelValue, (v) => { watch(() => props.modelValue, (v) => {
if (v !== content.value) { if (v !== content.value) {
content.value = v === undefined ? "<p></p>" : v; content.value = v === undefined ? "<p></p>" : v;
} }
}, { immediate: true }); }, { immediate: true });
// 图片上传成功返回图片地址 // 图片上传成功返回图片地址
const handleUploadSuccess = (res: any) => { const handleUploadSuccess = (res: any) => {
// 获取富文本实例 // 获取富文本实例
let quill = toRaw(myQuillEditor.value).getQuill(); let quill = toRaw(myQuillEditor.value).getQuill();
// 如果上传成功 // 如果上传成功
if (res.code === 200) { if (res.code === 200) {
// 获取光标位置 // 获取光标位置
let length = quill.selection.savedRange.index; let length = quill.selection.savedRange.index;
// 插入图片res为服务器返回的图片链接地址 // 插入图片res为服务器返回的图片链接地址
quill.insertEmbed(length, "image", res.data.url); quill.insertEmbed(length, "image", res.data.url);
// 调整光标到最后 // 调整光标到最后
quill.setSelection(length + 1); quill.setSelection(length + 1);
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
} else { } else {
proxy?.$modal.loading(res.msg); proxy?.$modal.loading(res.msg);
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
} }
} }
// 图片上传前拦截 // 图片上传前拦截
const handleBeforeUpload = (file: any) => { const handleBeforeUpload = (file: any) => {
// 校检文件大小 // 校检文件大小
if (props.fileSize) { if (props.fileSize) {
const isLt = file.size / 1024 / 1024 < props.fileSize; const isLt = file.size / 1024 / 1024 < props.fileSize;
if (!isLt) { if (!isLt) {
proxy?.$modal.msgError(`上传文件大小不能超过 ${props.fileSize} MB!`); proxy?.$modal.msgError(`上传文件大小不能超过 ${props.fileSize} MB!`);
return false; return false;
}
} }
} proxy?.$modal.loading('正在上传文件,请稍候...');
proxy?.$modal.loading('正在上传文件,请稍候...'); return true;
return true;
} }
// 图片失败拦截 // 图片失败拦截
const handleUploadError = (err: any) => { const handleUploadError = (err: any) => {
console.error(err); console.error(err);
proxy?.$modal.msgError('上传文件失败'); proxy?.$modal.msgError('上传文件失败');
} }
</script> </script>
<template>
<div>
<el-upload
:action="upload.url"
:before-upload="handleBeforeUpload"
:on-success="handleUploadSuccess"
:on-error="handleUploadError"
class="editor-img-uploader"
name="file"
:show-file-list="false"
:headers="upload.headers"
style="display: none"
v-if="type === 'url'"
>
</el-upload>
<div class="editor">
<quill-editor
ref="myQuillEditor"
v-model:content="content"
contentType="html"
@textChange="(e: any) => $emit('update:modelValue', content)"
:options="options"
:style="styles"
/>
</div>
</div>
</template>
<style> <style>
.editor, .ql-toolbar { .editor, .ql-toolbar {
white-space: pre-wrap !important; white-space: pre-wrap !important;

View File

@ -1,3 +1,47 @@
<template>
<div class="upload-file">
<el-upload
multiple
:action="uploadFileUrl"
:before-upload="handleBeforeUpload"
:file-list="fileList"
:limit="limit"
:on-error="handleUploadError"
:on-exceed="handleExceed"
:on-success="handleUploadSuccess"
:show-file-list="false"
:headers="headers"
class="upload-file-uploader"
ref="fileUploadRef"
>
<!-- 上传按钮 -->
<el-button type="primary">选取文件</el-button>
</el-upload>
<!-- 上传提示 -->
<div class="el-upload__tip" v-if="showTip">
请上传
<template v-if="fileSize">
大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b>
</template>
<template v-if="fileType">
格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b>
</template>
的文件
</div>
<!-- 文件列表 -->
<transition-group class="upload-file-list el-upload-list el-upload-list--text" name="el-fade-in-linear" tag="ul">
<li :key="file.uid" class="el-upload-list__item ele-upload-list__item-content" v-for="(file, index) in fileList">
<el-link :href="`${file.url}`" :underline="false" target="_blank">
<span class="el-icon-document"> {{ getFileName(file.name) }} </span>
</el-link>
<div class="ele-upload-list__item-content-action">
<el-link :underline="false" @click="handleDelete(index)" type="danger">删除</el-link>
</div>
</li>
</transition-group>
</div>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { getToken } from "@/utils/auth"; import { getToken } from "@/utils/auth";
import { listByIds, delOss } from "@/api/system/oss"; import { listByIds, delOss } from "@/api/system/oss";
@ -5,27 +49,27 @@ import { ComponentInternalInstance } from "vue";
import { ElUpload, UploadFile } from "element-plus"; import { ElUpload, UploadFile } from "element-plus";
const props = defineProps({ const props = defineProps({
modelValue: [String, Object, Array], modelValue: [String, Object, Array],
// 数量限制 // 数量限制
limit: { limit: {
type: Number, type: Number,
default: 5, default: 5,
}, },
// 大小限制(MB) // 大小限制(MB)
fileSize: { fileSize: {
type: Number, type: Number,
default: 5, default: 5,
}, },
// 文件类型, 例如['png', 'jpg', 'jpeg'] // 文件类型, 例如['png', 'jpg', 'jpeg']
fileType: { fileType: {
type: Array, type: Array,
default: () => ["doc", "xls", "ppt", "txt", "pdf"], default: () => ["doc", "xls", "ppt", "txt", "pdf"],
}, },
// 是否显示提示 // 是否显示提示
isShowTip: { isShowTip: {
type: Boolean, type: Boolean,
default: true default: true
} }
}); });
const { proxy } = getCurrentInstance() as ComponentInternalInstance; const { proxy } = getCurrentInstance() as ComponentInternalInstance;
@ -39,172 +83,128 @@ const headers = ref({ Authorization: "Bearer " + getToken() });
const fileList = ref<any[]>([]); const fileList = ref<any[]>([]);
const showTip = computed( const showTip = computed(
() => props.isShowTip && (props.fileType || props.fileSize) () => props.isShowTip && (props.fileType || props.fileSize)
); );
const fileUploadRef = ref(ElUpload); const fileUploadRef = ref(ElUpload);
watch(() => props.modelValue, async val => { watch(() => props.modelValue, async val => {
if (val) { if (val) {
let temp = 1; let temp = 1;
// 首先将值转为数组 // 首先将值转为数组
let list = []; let list = [];
if (Array.isArray(val)) { if (Array.isArray(val)) {
list = val; list = val;
} else { } else {
const res = await listByIds(val as string) const res = await listByIds(val as string)
list = res.data.map((oss) => { list = res.data.map((oss) => {
const data = { name: oss.originalName, url: oss.url, ossId: oss.ossId }; const data = { name: oss.originalName, url: oss.url, ossId: oss.ossId };
return data; return data;
});
}
// 然后将数组转为对象数组
fileList.value = list.map(item => {
item = {name: item.name, url: item.url, ossId: item.ossId};
item.uid = item.uid || new Date().getTime() + temp++;
return item;
}); });
} else {
fileList.value = [];
return [];
} }
// 然后将数组转为对象数组
fileList.value = list.map(item => {
item = {name: item.name, url: item.url, ossId: item.ossId};
item.uid = item.uid || new Date().getTime() + temp++;
return item;
});
} else {
fileList.value = [];
return [];
}
},{ deep: true, immediate: true }); },{ deep: true, immediate: true });
// 上传前校检格式和大小 // 上传前校检格式和大小
const handleBeforeUpload = (file: any) => { const handleBeforeUpload = (file: any) => {
// 校检文件类型 // 校检文件类型
if (props.fileType.length) { if (props.fileType.length) {
const fileName = file.name.split('.'); const fileName = file.name.split('.');
const fileExt = fileName[fileName.length - 1]; const fileExt = fileName[fileName.length - 1];
const isTypeOk = props.fileType.indexOf(fileExt) >= 0; const isTypeOk = props.fileType.indexOf(fileExt) >= 0;
if (!isTypeOk) { if (!isTypeOk) {
proxy?.$modal.msgError(`文件格式不正确, 请上传${props.fileType.join("/")}格式文件!`); proxy?.$modal.msgError(`文件格式不正确, 请上传${props.fileType.join("/")}格式文件!`);
return false; return false;
}
} }
} // 校检文件大小
// 校检文件大小 if (props.fileSize) {
if (props.fileSize) { const isLt = file.size / 1024 / 1024 < props.fileSize;
const isLt = file.size / 1024 / 1024 < props.fileSize; if (!isLt) {
if (!isLt) { proxy?.$modal.msgError(`上传文件大小不能超过 ${props.fileSize} MB!`);
proxy?.$modal.msgError(`上传文件大小不能超过 ${props.fileSize} MB!`); return false;
return false; }
} }
} proxy?.$modal.loading("正在上传文件,请稍候...");
proxy?.$modal.loading("正在上传文件,请稍候..."); number.value++;
number.value++; return true;
return true;
} }
// 文件个数超出 // 文件个数超出
const handleExceed = () => { const handleExceed = () => {
proxy?.$modal.msgError(`上传文件数量不能超过 ${props.limit} 个!`); proxy?.$modal.msgError(`上传文件数量不能超过 ${props.limit} 个!`);
} }
// 上传失败 // 上传失败
const handleUploadError = () => { const handleUploadError = () => {
proxy?.$modal.msgError("上传文件失败"); proxy?.$modal.msgError("上传文件失败");
} }
// 上传成功回调 // 上传成功回调
const handleUploadSuccess = (res:any, file: UploadFile) => { const handleUploadSuccess = (res:any, file: UploadFile) => {
if (res.code === 200) { if (res.code === 200) {
uploadList.value.push({ name: res.data.fileName, url: res.data.url, ossId: res.data.ossId }); uploadList.value.push({ name: res.data.fileName, url: res.data.url, ossId: res.data.ossId });
uploadedSuccessfully(); uploadedSuccessfully();
} else { } else {
number.value--; number.value--;
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
proxy?.$modal.msgError(res.msg); proxy?.$modal.msgError(res.msg);
fileUploadRef.value.handleRemove(file); fileUploadRef.value.handleRemove(file);
uploadedSuccessfully(); uploadedSuccessfully();
} }
} }
// 删除文件 // 删除文件
const handleDelete = (index: number) => { const handleDelete = (index: number) => {
let ossId = fileList.value[index].ossId; let ossId = fileList.value[index].ossId;
delOss(ossId); delOss(ossId);
fileList.value.splice(index, 1); fileList.value.splice(index, 1);
emit("update:modelValue", listToString(fileList.value)); emit("update:modelValue", listToString(fileList.value));
} }
// 上传结束处理 // 上传结束处理
const uploadedSuccessfully =() => { const uploadedSuccessfully =() => {
if (number.value > 0 && uploadList.value.length === number.value) { if (number.value > 0 && uploadList.value.length === number.value) {
fileList.value = fileList.value.filter(f => f.url !== undefined).concat(uploadList.value); fileList.value = fileList.value.filter(f => f.url !== undefined).concat(uploadList.value);
uploadList.value = []; uploadList.value = [];
number.value = 0; number.value = 0;
emit("update:modelValue", listToString(fileList.value)); emit("update:modelValue", listToString(fileList.value));
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
} }
} }
// 获取文件名称 // 获取文件名称
const getFileName = (name: string) => { const getFileName = (name: string) => {
// 如果是url那么取最后的名字 如果不是直接返回 // 如果是url那么取最后的名字 如果不是直接返回
if (name.lastIndexOf("/") > -1) { if (name.lastIndexOf("/") > -1) {
return name.slice(name.lastIndexOf("/") + 1); return name.slice(name.lastIndexOf("/") + 1);
} else { } else {
return name; return name;
} }
} }
// 对象转成指定字符串分隔 // 对象转成指定字符串分隔
const listToString = (list: any[], separator?: string) => { const listToString = (list: any[], separator?: string) => {
let strs = ""; let strs = "";
separator = separator || ","; separator = separator || ",";
list.forEach(item => { list.forEach(item => {
if (item.ossId) { if (item.ossId) {
strs += item.ossId + separator; strs += item.ossId + separator;
} }
}) })
return strs != "" ? strs.substring(0, strs.length - 1) : ""; return strs != "" ? strs.substring(0, strs.length - 1) : "";
} }
</script> </script>
<template>
<div class="upload-file">
<el-upload
multiple
:action="uploadFileUrl"
:before-upload="handleBeforeUpload"
:file-list="fileList"
:limit="limit"
:on-error="handleUploadError"
:on-exceed="handleExceed"
:on-success="handleUploadSuccess"
:show-file-list="false"
:headers="headers"
class="upload-file-uploader"
ref="fileUploadRef"
>
<!-- 上传按钮 -->
<el-button type="primary">选取文件</el-button>
</el-upload>
<!-- 上传提示 -->
<div class="el-upload__tip" v-if="showTip">
请上传
<template v-if="fileSize">
大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b>
</template>
<template v-if="fileType">
格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b>
</template>
的文件
</div>
<!-- 文件列表 -->
<transition-group class="upload-file-list el-upload-list el-upload-list--text" name="el-fade-in-linear" tag="ul">
<li :key="file.uid" class="el-upload-list__item ele-upload-list__item-content" v-for="(file, index) in fileList">
<el-link :href="`${file.url}`" :underline="false" target="_blank">
<span class="el-icon-document"> {{ getFileName(file.name) }} </span>
</el-link>
<div class="ele-upload-list__item-content-action">
<el-link :underline="false" @click="handleDelete(index)" type="danger">删除</el-link>
</div>
</li>
</transition-group>
</div>
</template>
<style scoped lang="scss"> <style scoped lang="scss">
.upload-file-uploader { .upload-file-uploader {
margin-bottom: 5px; margin-bottom: 5px;

View File

@ -13,13 +13,13 @@ const toggleClick = () => {
</script> </script>
<template> <template>
<div style="padding: 0 15px;" @click="toggleClick"> <div style="padding: 0 15px;" @click="toggleClick">
<svg :class="{'is-active':isActive}" class="hamburger" viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg" width="64" height="64"> <svg :class="{'is-active':isActive}" class="hamburger" viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg" width="64" height="64">
<path <path
d="M408 442h480c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8H408c-4.4 0-8 3.6-8 8v56c0 4.4 3.6 8 8 8zm-8 204c0 4.4 3.6 8 8 8h480c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8H408c-4.4 0-8 3.6-8 8v56zm504-486H120c-4.4 0-8 3.6-8 8v56c0 4.4 3.6 8 8 8h784c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8zm0 632H120c-4.4 0-8 3.6-8 8v56c0 4.4 3.6 8 8 8h784c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8zM142.4 642.1L298.7 519a8.84 8.84 0 0 0 0-13.9L142.4 381.9c-5.8-4.6-14.4-.5-14.4 6.9v246.3a8.9 8.9 0 0 0 14.4 7z" d="M408 442h480c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8H408c-4.4 0-8 3.6-8 8v56c0 4.4 3.6 8 8 8zm-8 204c0 4.4 3.6 8 8 8h480c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8H408c-4.4 0-8 3.6-8 8v56zm504-486H120c-4.4 0-8 3.6-8 8v56c0 4.4 3.6 8 8 8h784c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8zm0 632H120c-4.4 0-8 3.6-8 8v56c0 4.4 3.6 8 8 8h784c4.4 0 8-3.6 8-8v-56c0-4.4-3.6-8-8-8zM142.4 642.1L298.7 519a8.84 8.84 0 0 0 0-13.9L142.4 381.9c-5.8-4.6-14.4-.5-14.4 6.9v246.3a8.9 8.9 0 0 0 14.4 7z"
/> />
</svg> </svg>
</div> </div>
</template> </template>
<style scoped> <style scoped>

View File

@ -122,22 +122,22 @@ watch(searchPool, (list) => {
</script> </script>
<template> <template>
<div :class="{ 'show': show }" class="header-search"> <div :class="{ 'show': show }" class="header-search">
<svg-icon class-name="search-icon" icon-class="search" @click.stop="click" /> <svg-icon class-name="search-icon" icon-class="search" @click.stop="click" />
<el-select <el-select
ref="headerSearchSelectRef" ref="headerSearchSelectRef"
v-model="search" v-model="search"
:remote-method="querySearch" :remote-method="querySearch"
filterable filterable
default-first-option default-first-option
remote remote
placeholder="Search" placeholder="Search"
class="header-search-select" class="header-search-select"
@change="change" @change="change"
> >
<el-option v-for="option in options" :key="option.item.path" :value="option.item" :label="option.item.title.join(' > ')" /> <el-option v-for="option in options" :key="option.item.path" :value="option.item" :label="option.item.title.join(' > ')" />
</el-select> </el-select>
</div> </div>
</template> </template>
<style lang="scss" scoped> <style lang="scss" scoped>

View File

@ -44,34 +44,34 @@ const selectedIcon = (iconName: string) => {
</script> </script>
<template> <template>
<div class="relative" :style="{ width: width }"> <div class="relative" :style="{ width: width }">
<el-input v-model="modelValue" readonly @click="visible = !visible" placeholder="点击选择图标"> <el-input v-model="modelValue" readonly @click="visible = !visible" placeholder="点击选择图标">
<template #prepend> <template #prepend>
<svg-icon :icon-class="modelValue as string"></svg-icon> <svg-icon :icon-class="modelValue as string"></svg-icon>
</template> </template>
</el-input> </el-input>
<el-popover shadow="none" :visible="visible" placement="bottom-end" trigger="click" :width="450"> <el-popover shadow="none" :visible="visible" placement="bottom-end" trigger="click" :width="450">
<template #reference> <template #reference>
<div @click="visible = !visible" class="cursor-pointer text-[#999] absolute right-[10px] top-0 height-[32px] leading-[32px]"> <div @click="visible = !visible" class="cursor-pointer text-[#999] absolute right-[10px] top-0 height-[32px] leading-[32px]">
<i-ep-caret-top v-show="visible"></i-ep-caret-top> <i-ep-caret-top v-show="visible"></i-ep-caret-top>
<i-ep-caret-bottom v-show="!visible"></i-ep-caret-bottom> <i-ep-caret-bottom v-show="!visible"></i-ep-caret-bottom>
</div> </div>
</template> </template>
<el-input class="p-2" v-model="filterValue" placeholder="搜索图标" clearable @input="filterIcons" /> <el-input class="p-2" v-model="filterValue" placeholder="搜索图标" clearable @input="filterIcons" />
<el-scrollbar height="w-[200px]"> <el-scrollbar height="w-[200px]">
<ul class="icon-list"> <ul class="icon-list">
<el-tooltip v-for="(iconName, index) in iconNames" :key="index" :content="iconName" placement="bottom" effect="light"> <el-tooltip v-for="(iconName, index) in iconNames" :key="index" :content="iconName" placement="bottom" effect="light">
<li class="icon-item" @click="selectedIcon(iconName)"> <li class="icon-item" @click="selectedIcon(iconName)">
<svg-icon color="var(--el-text-color-regular)" :icon-class="iconName" /> <svg-icon color="var(--el-text-color-regular)" :icon-class="iconName" />
</li> </li>
</el-tooltip> </el-tooltip>
</ul> </ul>
</el-scrollbar> </el-scrollbar>
</el-popover> </el-popover>
</div> </div>
</template> </template>
<style scoped lang="scss"> <style scoped lang="scss">

View File

@ -1,7 +1,7 @@
const icons: string[] = []; const icons: string[] = [];
const modules = import.meta.glob('./../../assets/icons/svg/*.svg'); const modules = import.meta.glob('./../../assets/icons/svg/*.svg');
for (const path in modules) { for (const path in modules) {
const p = path.split('assets/icons/svg/')[1].split('.svg')[0]; const p = path.split('assets/icons/svg/')[1].split('.svg')[0];
icons.push(p); icons.push(p);
} }
export default icons; export default icons;

View File

@ -44,13 +44,13 @@ const realHeight = computed(() =>
</script> </script>
<template> <template>
<el-image :src="`${realSrc}`" fit="cover" :style="`width:${realWidth};height:${realHeight};`" :preview-src-list="realSrcList" preview-teleported> <el-image :src="`${realSrc}`" fit="cover" :style="`width:${realWidth};height:${realHeight};`" :preview-src-list="realSrcList" preview-teleported>
<template #error> <template #error>
<div class="image-slot"> <div class="image-slot">
<el-icon><picture-filled /></el-icon> <el-icon><picture-filled /></el-icon>
</div> </div>
</template> </template>
</el-image> </el-image>
</template> </template>
<style lang="scss" scoped> <style lang="scss" scoped>

View File

@ -1,3 +1,42 @@
<template>
<div class="component-upload-image">
<el-upload
multiple
:action="uploadImgUrl"
list-type="picture-card"
:on-success="handleUploadSuccess"
:before-upload="handleBeforeUpload"
:limit="limit"
:on-error="handleUploadError"
:on-exceed="handleExceed"
ref="imageUpload"
:before-remove="handleDelete"
:show-file-list="true"
:headers="headers"
:file-list="fileList"
:on-preview="handlePictureCardPreview"
:class="{ hide: fileList.length >= limit }"
>
<el-icon class="avatar-uploader-icon"><plus /></el-icon>
</el-upload>
<!-- 上传提示 -->
<div class="el-upload__tip" v-if="showTip">
请上传
<template v-if="fileSize">
大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b>
</template>
<template v-if="fileType">
格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b>
</template>
的文件
</div>
<el-dialog v-model="dialogVisible" title="预览" width="800px" append-to-body>
<img :src="dialogImageUrl" style="display: block; max-width: 100%; margin: 0 auto" />
</el-dialog>
</div>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { getToken } from "@/utils/auth"; import { getToken } from "@/utils/auth";
import { listByIds, delOss } from "@/api/system/oss"; import { listByIds, delOss } from "@/api/system/oss";
@ -6,27 +45,27 @@ import { OssVO } from "@/api/system/oss/types";
import { ElUpload, UploadFile } from "element-plus"; import { ElUpload, UploadFile } from "element-plus";
const props = defineProps({ const props = defineProps({
modelValue: [String, Object, Array], modelValue: [String, Object, Array],
// 图片数量限制 // 图片数量限制
limit: { limit: {
type: Number, type: Number,
default: 5, default: 5,
}, },
// 大小限制(MB) // 大小限制(MB)
fileSize: { fileSize: {
type: Number, type: Number,
default: 5, default: 5,
}, },
// 文件类型, 例如['png', 'jpg', 'jpeg'] // 文件类型, 例如['png', 'jpg', 'jpeg']
fileType: { fileType: {
type: Array as PropType<string[]>, type: Array as PropType<string[]>,
default: () => ["png", "jpg", "jpeg"], default: () => ["png", "jpg", "jpeg"],
}, },
// 是否显示提示 // 是否显示提示
isShowTip: { isShowTip: {
type: Boolean, type: Boolean,
default: true default: true
}, },
}); });
const { proxy } = getCurrentInstance() as ComponentInternalInstance; const { proxy } = getCurrentInstance() as ComponentInternalInstance;
@ -42,179 +81,140 @@ const headers = ref({ Authorization: "Bearer " + getToken() });
const fileList = ref<any[]>([]); const fileList = ref<any[]>([]);
const showTip = computed( const showTip = computed(
() => props.isShowTip && (props.fileType || props.fileSize) () => props.isShowTip && (props.fileType || props.fileSize)
); );
const imageUploadRef = ref(ElUpload); const imageUploadRef = ref(ElUpload);
watch(() => props.modelValue, async val => { watch(() => props.modelValue, async val => {
if (val) { if (val) {
// 首先将值转为数组 // 首先将值转为数组
let list:OssVO[] = []; let list:OssVO[] = [];
if (Array.isArray(val)) { if (Array.isArray(val)) {
list = val as OssVO[]; list = val as OssVO[];
} else {
const res = await listByIds(val as string)
list = res.data
}
// 然后将数组转为对象数组
fileList.value = list.map(item => {
// 字符串回显处理 如果此处存的是url可直接回显 如果存的是id需要调用接口查出来
let itemData;
if (typeof item === "string") {
itemData = { name: item, url: item };
} else {
// 此处name使用ossId 防止删除出现重名
itemData = { name: item.ossId, url: item.url, ossId: item.ossId };
}
return itemData;
});
} else { } else {
const res = await listByIds(val as string) fileList.value = [];
list = res.data return [];
} }
// 然后将数组转为对象数组
fileList.value = list.map(item => {
// 字符串回显处理 如果此处存的是url可直接回显 如果存的是id需要调用接口查出来
let itemData;
if (typeof item === "string") {
itemData = { name: item, url: item };
} else {
// 此处name使用ossId 防止删除出现重名
itemData = { name: item.ossId, url: item.url, ossId: item.ossId };
}
return itemData;
});
} else {
fileList.value = [];
return [];
}
},{ deep: true, immediate: true }); },{ deep: true, immediate: true });
/** 上传前loading加载 */ /** 上传前loading加载 */
const handleBeforeUpload = (file: any) => { const handleBeforeUpload = (file: any) => {
let isImg = false; let isImg = false;
if (props.fileType.length) { if (props.fileType.length) {
let fileExtension = ""; let fileExtension = "";
if (file.name.lastIndexOf(".") > -1) { if (file.name.lastIndexOf(".") > -1) {
fileExtension = file.name.slice(file.name.lastIndexOf(".") + 1); fileExtension = file.name.slice(file.name.lastIndexOf(".") + 1);
}
isImg = props.fileType.some((type) => {
if (file.type.indexOf(type) > -1) return true;
if (fileExtension && fileExtension.indexOf(type) > -1) return true;
return false;
});
} else {
isImg = file.type.indexOf("image") > -1;
} }
isImg = props.fileType.some((type) => { if (!isImg) {
if (file.type.indexOf(type) > -1) return true; proxy?.$modal.msgError(
if (fileExtension && fileExtension.indexOf(type) > -1) return true; `文件格式不正确, 请上传${props.fileType.join("/")}图片格式文件!`
return false; );
}); return false;
} else {
isImg = file.type.indexOf("image") > -1;
}
if (!isImg) {
proxy?.$modal.msgError(
`文件格式不正确, 请上传${props.fileType.join("/")}图片格式文件!`
);
return false;
}
if (props.fileSize) {
const isLt = file.size / 1024 / 1024 < props.fileSize;
if (!isLt) {
proxy?.$modal.msgError(`上传头像图片大小不能超过 ${props.fileSize} MB!`);
return false;
} }
} if (props.fileSize) {
proxy?.$modal.loading("正在上传图片,请稍候..."); const isLt = file.size / 1024 / 1024 < props.fileSize;
number.value++; if (!isLt) {
proxy?.$modal.msgError(`上传头像图片大小不能超过 ${props.fileSize} MB!`);
return false;
}
}
proxy?.$modal.loading("正在上传图片,请稍候...");
number.value++;
} }
// 文件个数超出 // 文件个数超出
const handleExceed = () => { const handleExceed = () => {
proxy?.$modal.msgError(`上传文件数量不能超过 ${props.limit} 个!`); proxy?.$modal.msgError(`上传文件数量不能超过 ${props.limit} 个!`);
} }
// 上传成功回调 // 上传成功回调
const handleUploadSuccess = (res: any, file: UploadFile) => { const handleUploadSuccess = (res: any, file: UploadFile) => {
if (res.code === 200) { if (res.code === 200) {
uploadList.value.push({ name: res.data.fileName, url: res.data.url, ossId: res.data.ossId }); uploadList.value.push({ name: res.data.fileName, url: res.data.url, ossId: res.data.ossId });
uploadedSuccessfully(); uploadedSuccessfully();
} else { } else {
number.value--; number.value--;
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
proxy?.$modal.msgError(res.msg); proxy?.$modal.msgError(res.msg);
imageUploadRef.value.handleRemove(file); imageUploadRef.value.handleRemove(file);
uploadedSuccessfully(); uploadedSuccessfully();
} }
} }
// 删除图片 // 删除图片
const handleDelete = (file: UploadFile): boolean => { const handleDelete = (file: UploadFile): boolean => {
const findex = fileList.value.map(f => f.name).indexOf(file.name); const findex = fileList.value.map(f => f.name).indexOf(file.name);
if (findex > -1 && uploadList.value.length === number.value) { if (findex > -1 && uploadList.value.length === number.value) {
let ossId = fileList.value[findex].ossId; let ossId = fileList.value[findex].ossId;
delOss(ossId); delOss(ossId);
fileList.value.splice(findex, 1); fileList.value.splice(findex, 1);
emit("update:modelValue", listToString(fileList.value)); emit("update:modelValue", listToString(fileList.value));
return false; return false;
} }
return true; return true;
} }
// 上传结束处理 // 上传结束处理
const uploadedSuccessfully = () => { const uploadedSuccessfully = () => {
if (number.value > 0 && uploadList.value.length === number.value) { if (number.value > 0 && uploadList.value.length === number.value) {
fileList.value = fileList.value.filter(f => f.url !== undefined).concat(uploadList.value); fileList.value = fileList.value.filter(f => f.url !== undefined).concat(uploadList.value);
uploadList.value = []; uploadList.value = [];
number.value = 0; number.value = 0;
emit("update:modelValue", listToString(fileList.value)); emit("update:modelValue", listToString(fileList.value));
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
} }
} }
// 上传失败 // 上传失败
const handleUploadError = () => { const handleUploadError = () => {
proxy?.$modal.msgError("上传图片失败"); proxy?.$modal.msgError("上传图片失败");
proxy?.$modal.closeLoading(); proxy?.$modal.closeLoading();
} }
// 预览 // 预览
const handlePictureCardPreview = (file: any) => { const handlePictureCardPreview = (file: any) => {
dialogImageUrl.value = file.url; dialogImageUrl.value = file.url;
dialogVisible.value = true; dialogVisible.value = true;
} }
// 对象转成指定字符串分隔 // 对象转成指定字符串分隔
const listToString = (list: any[], separator?: string) => { const listToString = (list: any[], separator?: string) => {
let strs = ""; let strs = "";
separator = separator || ","; separator = separator || ",";
for (let i in list) { for (let i in list) {
if(undefined !== list[i].ossId && list[i].url.indexOf("blob:") !== 0) { if(undefined !== list[i].ossId && list[i].url.indexOf("blob:") !== 0) {
strs += list[i].ossId + separator; strs += list[i].ossId + separator;
}
} }
} return strs != "" ? strs.substring(0, strs.length - 1) : "";
return strs != "" ? strs.substring(0, strs.length - 1) : "";
} }
</script> </script>
<template>
<div class="component-upload-image">
<el-upload
multiple
:action="uploadImgUrl"
list-type="picture-card"
:on-success="handleUploadSuccess"
:before-upload="handleBeforeUpload"
:limit="limit"
:on-error="handleUploadError"
:on-exceed="handleExceed"
ref="imageUpload"
:before-remove="handleDelete"
:show-file-list="true"
:headers="headers"
:file-list="fileList"
:on-preview="handlePictureCardPreview"
:class="{ hide: fileList.length >= limit }"
>
<el-icon class="avatar-uploader-icon"><plus /></el-icon>
</el-upload>
<!-- 上传提示 -->
<div class="el-upload__tip" v-if="showTip">
请上传
<template v-if="fileSize">
大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b>
</template>
<template v-if="fileType">
格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b>
</template>
的文件
</div>
<el-dialog v-model="dialogVisible" title="预览" width="800px" append-to-body>
<img :src="dialogImageUrl" style="display: block; max-width: 100%; margin: 0 auto" />
</el-dialog>
</div>
</template>
<style scoped lang="scss"> <style scoped lang="scss">
// .el-upload--picture-card 控制加号部分 // .el-upload--picture-card 控制加号部分
:deep(.hide .el-upload--picture-card) { :deep(.hide .el-upload--picture-card) {

View File

@ -1,6 +1,22 @@
<template>
<div :class="{ 'hidden': hidden }" class="pagination-container">
<el-pagination
:background="background"
v-model:current-page="currentPage"
v-model:page-size="pageSize"
:layout="layout"
:page-sizes="pageSizes"
:pager-count="pagerCount"
:total="total"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
/>
</div>
</template>
<script lang="ts"> <script lang="ts">
export default { export default {
name: 'Pagination' name: 'Pagination'
} }
</script> </script>
@ -9,101 +25,85 @@ import { scrollTo } from '@/utils/scroll-to'
import { PropType } from "vue"; import { PropType } from "vue";
const props = defineProps({ const props = defineProps({
total: { total: {
required: true, required: true,
type: Number type: Number
}, },
page: { page: {
type: Number, type: Number,
default: 1 default: 1
}, },
limit: { limit: {
type: Number, type: Number,
default: 20 default: 20
}, },
pageSizes: { pageSizes: {
type: Array as PropType<number[]>, type: Array as PropType<number[]>,
default() { default() {
return [10, 20, 30, 50] return [10, 20, 30, 50]
}
},
// 移动端页码按钮的数量端默认值5
pagerCount: {
type: Number,
default: document.body.clientWidth < 992 ? 5 : 7
},
layout: {
type: String,
default: 'total, sizes, prev, pager, next, jumper'
},
background: {
type: Boolean,
default: true
},
autoScroll: {
type: Boolean,
default: true
},
hidden: {
type: Boolean,
default: false
},
float: {
type: String,
default: 'right'
} }
},
// 移动端页码按钮的数量端默认值5
pagerCount: {
type: Number,
default: document.body.clientWidth < 992 ? 5 : 7
},
layout: {
type: String,
default: 'total, sizes, prev, pager, next, jumper'
},
background: {
type: Boolean,
default: true
},
autoScroll: {
type: Boolean,
default: true
},
hidden: {
type: Boolean,
default: false
},
float: {
type: String,
default: 'right'
}
}) })
const emit = defineEmits(['update:page', 'update:limit', 'pagination']); const emit = defineEmits(['update:page', 'update:limit', 'pagination']);
const currentPage = computed({ const currentPage = computed({
get() { get() {
return props.page return props.page
}, },
set(val) { set(val) {
emit('update:page', val) emit('update:page', val)
} }
}) })
const pageSize = computed({ const pageSize = computed({
get() { get() {
return props.limit return props.limit
}, },
set(val){ set(val){
emit('update:limit', val) emit('update:limit', val)
} }
}) })
function handleSizeChange(val: number) { function handleSizeChange(val: number) {
if (currentPage.value * val > props.total) { if (currentPage.value * val > props.total) {
currentPage.value = 1 currentPage.value = 1
} }
emit('pagination', { page: currentPage.value, limit: val }) emit('pagination', { page: currentPage.value, limit: val })
if (props.autoScroll) { if (props.autoScroll) {
scrollTo(0, 800) scrollTo(0, 800)
} }
} }
function handleCurrentChange(val: number) { function handleCurrentChange(val: number) {
emit('pagination', { page: val, limit: pageSize.value }) emit('pagination', { page: val, limit: pageSize.value })
if (props.autoScroll) { if (props.autoScroll) {
scrollTo(0, 800) scrollTo(0, 800)
} }
} }
</script> </script>
<template>
<div :class="{ 'hidden': hidden }" class="pagination-container">
<el-pagination
:background="background"
v-model:current-page="currentPage"
v-model:page-size="pageSize"
:layout="layout"
:page-sizes="pageSizes"
:pager-count="pagerCount"
:total="total"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
/>
</div>
</template>
<style lang="scss" scoped> <style lang="scss" scoped>
.pagination-container { .pagination-container {
background: #fff; background: #fff;

View File

@ -1,3 +1,3 @@
<template> <template>
<router-view /> <router-view />
</template> </template>

View File

@ -1,23 +1,42 @@
<template>
<div class="top-right-btn" :style="style">
<el-row>
<el-tooltip class="item" effect="dark" :content="showSearch ? '隐藏搜索' : '显示搜索'" placement="top" v-if="search">
<el-button circle icon="Search" @click="toggleSearch()" />
</el-tooltip>
<el-tooltip class="item" effect="dark" content="刷新" placement="top">
<el-button circle icon="Refresh" @click="refresh()" />
</el-tooltip>
<el-tooltip class="item" effect="dark" content="显隐列" placement="top" v-if="columns">
<el-button circle icon="Menu" @click="showColumn()" />
</el-tooltip>
</el-row>
<el-dialog :title="title" v-model="open" append-to-body>
<el-transfer :titles="['显示', '隐藏']" v-model="value" :data="columns" @change="dataChange"></el-transfer>
</el-dialog>
</div>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { TransferKey } from "element-plus"; import { TransferKey } from "element-plus";
import { PropType } from "vue"; import { PropType } from "vue";
const props = defineProps({ const props = defineProps({
showSearch: { showSearch: {
type: Boolean, type: Boolean,
default: true, default: true,
}, },
columns: { columns: {
type: Array as PropType<FieldOption[]>, type: Array as PropType<FieldOption[]>,
}, },
search: { search: {
type: Boolean, type: Boolean,
default: true, default: true,
}, },
gutter: { gutter: {
type: Number, type: Number,
default: 10, default: 10,
}, },
}) })
const emits = defineEmits(['update:showSearch', 'queryTable']); const emits = defineEmits(['update:showSearch', 'queryTable']);
@ -30,64 +49,45 @@ const title = ref("显示/隐藏");
const open = ref(false); const open = ref(false);
const style = computed(() => { const style = computed(() => {
const ret: any = {}; const ret: any = {};
if (props.gutter) { if (props.gutter) {
ret.marginRight = `${props.gutter / 2}px`; ret.marginRight = `${props.gutter / 2}px`;
} }
return ret; return ret;
}); });
// 搜索 // 搜索
function toggleSearch() { function toggleSearch() {
emits("update:showSearch", !props.showSearch); emits("update:showSearch", !props.showSearch);
} }
// 刷新 // 刷新
function refresh() { function refresh() {
emits("queryTable"); emits("queryTable");
} }
// 右侧列表元素变化 // 右侧列表元素变化
function dataChange(data: TransferKey[]) { function dataChange(data: TransferKey[]) {
props.columns?.forEach((item) => { props.columns?.forEach((item) => {
item.visible = !data.includes(item.key); item.visible = !data.includes(item.key);
}) })
} }
// 打开显隐列dialog // 打开显隐列dialog
const showColumn = () => { const showColumn = () => {
open.value = true; open.value = true;
} }
// 显隐列初始默认隐藏列 // 显隐列初始默认隐藏列
onMounted(() => { onMounted(() => {
props.columns?.forEach((item) => { props.columns?.forEach((item) => {
if (!item.visible) { if (!item.visible) {
value.value.push(item.key); value.value.push(item.key);
} }
}) })
}) })
</script> </script>
<template>
<div class="top-right-btn" :style="style">
<el-row>
<el-tooltip class="item" effect="dark" :content="showSearch ? '隐藏搜索' : '显示搜索'" placement="top" v-if="search">
<el-button circle icon="Search" @click="toggleSearch()" />
</el-tooltip>
<el-tooltip class="item" effect="dark" content="刷新" placement="top">
<el-button circle icon="Refresh" @click="refresh()" />
</el-tooltip>
<el-tooltip class="item" effect="dark" content="显隐列" placement="top" v-if="columns">
<el-button circle icon="Menu" @click="showColumn()" />
</el-tooltip>
</el-row>
<el-dialog :title="title" v-model="open" append-to-body>
<el-transfer :titles="['显示', '隐藏']" v-model="value" :data="columns" @change="dataChange"></el-transfer>
</el-dialog>
</div>
</template>
<style lang="scss" scoped> <style lang="scss" scoped>
:deep(.el-transfer__button) { :deep(.el-transfer__button) {
border-radius: 50%; border-radius: 50%;

View File

@ -1,7 +1,7 @@
<template> <template>
<div> <div>
<svg-icon icon-class="question" @click="goto" /> <svg-icon icon-class="question" @click="goto" />
</div> </div>
</template> </template>
<script setup> <script setup>

View File

@ -1,7 +1,7 @@
<template> <template>
<div> <div>
<svg-icon icon-class="github" @click="goto" /> <svg-icon icon-class="github" @click="goto" />
</div> </div>
</template> </template>
<script setup> <script setup>

View File

@ -1,7 +1,7 @@
<template> <template>
<div> <div>
<svg-icon :icon-class="isFullscreen ? 'exit-fullscreen' : 'fullscreen'" @click="toggle" /> <svg-icon :icon-class="isFullscreen ? 'exit-fullscreen' : 'fullscreen'" @click="toggle" />
</div> </div>
</template> </template>
<script setup lang="ts"> <script setup lang="ts">

View File

@ -16,20 +16,20 @@ const handleSetSize = (size: string) => {
</script> </script>
<template> <template>
<div> <div>
<el-dropdown trigger="click" @command="handleSetSize"> <el-dropdown trigger="click" @command="handleSetSize">
<div class="size-icon--style"> <div class="size-icon--style">
<svg-icon class-name="size-icon" icon-class="size" /> <svg-icon class-name="size-icon" icon-class="size" />
</div> </div>
<template #dropdown> <template #dropdown>
<el-dropdown-menu> <el-dropdown-menu>
<el-dropdown-item v-for="item of sizeOptions" :key="item.value" :disabled="size === item.value" :command="item.value"> <el-dropdown-item v-for="item of sizeOptions" :key="item.value" :disabled="size === item.value" :command="item.value">
{{ item.label }} {{ item.label }}
</el-dropdown-item> </el-dropdown-item>
</el-dropdown-menu> </el-dropdown-menu>
</template> </template>
</el-dropdown> </el-dropdown>
</div> </div>
</template> </template>
<style lang="scss" scoped> <style lang="scss" scoped>

View File

@ -23,9 +23,9 @@ const svgClass = computed(() => {
</script> </script>
<template> <template>
<svg :class="svgClass" aria-hidden="true"> <svg :class="svgClass" aria-hidden="true">
<use :xlink:href="iconName" :fill="color" /> <use :xlink:href="iconName" :fill="color" />
</svg> </svg>
</template> </template>
<style scope lang="scss"> <style scope lang="scss">

View File

@ -1,3 +1,23 @@
<template>
<el-menu :default-active="activeMenu" mode="horizontal" @select="handleSelect" :ellipsis="false">
<template v-for="(item, index) in topMenus">
<el-menu-item :style="{'--theme': theme}" :index="item.path" :key="index" v-if="index < visibleNumber"
><svg-icon :icon-class="item.meta ? item.meta.icon : '' " /> {{ item.meta?.title }}</el-menu-item
>
</template>
<!-- 顶部菜单超出数量折叠 -->
<el-sub-menu :style="{'--theme': theme}" index="more" v-if="topMenus.length > visibleNumber">
<template #title>更多菜单</template>
<template v-for="(item, index) in topMenus">
<el-menu-item :index="item.path" :key="index" v-if="index >= visibleNumber"
><svg-icon :icon-class="item.meta ? item.meta.icon : '' " /> {{ item.meta?.title }}</el-menu-item
>
</template>
</el-sub-menu>
</el-menu>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { constantRoutes } from '@/router'; import { constantRoutes } from '@/router';
import { isHttp } from '@/utils/validate'; import { isHttp } from '@/utils/validate';
@ -130,26 +150,6 @@ onMounted(() => {
}) })
</script> </script>
<template>
<el-menu :default-active="activeMenu" mode="horizontal" @select="handleSelect" :ellipsis="false">
<template v-for="(item, index) in topMenus">
<el-menu-item :style="{'--theme': theme}" :index="item.path" :key="index" v-if="index < visibleNumber"
><svg-icon :icon-class="item.meta ? item.meta.icon : '' " /> {{ item.meta?.title }}</el-menu-item
>
</template>
<!-- 顶部菜单超出数量折叠 -->
<el-sub-menu :style="{'--theme': theme}" index="more" v-if="topMenus.length > visibleNumber">
<template #title>更多菜单</template>
<template v-for="(item, index) in topMenus">
<el-menu-item :index="item.path" :key="index" v-if="index >= visibleNumber"
><svg-icon :icon-class="item.meta ? item.meta.icon : '' " /> {{ item.meta?.title }}</el-menu-item
>
</template>
</el-sub-menu>
</el-menu>
</template>
<style lang="scss"> <style lang="scss">
.topmenu-container.el-menu--horizontal > .el-menu-item { .topmenu-container.el-menu--horizontal > .el-menu-item {
float: left; float: left;

View File

@ -128,31 +128,31 @@ ul li .el-tree .el-tree-node__content {
</style> </style>
<template> <template>
<div class="el-tree-select"> <div class="el-tree-select">
<el-select <el-select
style="width: 100%" style="width: 100%"
v-model="valueId" v-model="valueId"
ref="treeSelect" ref="treeSelect"
:filterable="true" :filterable="true"
:clearable="true" :clearable="true"
@clear="clearHandle" @clear="clearHandle"
:filter-method="selectFilterData" :filter-method="selectFilterData"
:placeholder="placeholder" :placeholder="placeholder"
> >
<el-option :value="valueId" :label="valueTitle"> <el-option :value="valueId" :label="valueTitle">
<el-tree <el-tree
id="tree-option" id="tree-option"
ref="selectTree" ref="selectTree"
:accordion="accordion" :accordion="accordion"
:data="options" :data="options"
:props="objMap" :props="objMap"
:node-key="objMap.value" :node-key="objMap.value"
:expand-on-click-node="false" :expand-on-click-node="false"
:default-expanded-keys="defaultExpandedKey" :default-expanded-keys="defaultExpandedKey"
:filter-node-method="filterNode" :filter-node-method="filterNode"
@node-click="handleNodeClick" @node-click="handleNodeClick"
></el-tree> ></el-tree>
</el-option> </el-option>
</el-select> </el-select>
</div> </div>
</template> </template>

View File

@ -21,7 +21,7 @@ onMounted(() => {
</script> </script>
<template> <template>
<div v-loading="loading" :style="'height:' + height"> <div v-loading="loading" :style="'height:' + height">
<iframe :src="url" frameborder="no" style="width: 100%; height: 100%" scrolling="auto" /> <iframe :src="url" frameborder="no" style="width: 100%; height: 100%" scrolling="auto" />
</div> </div>
</template> </template>

View File

@ -4,63 +4,63 @@
*/ */
export default { export default {
beforeMount(el: any, { value, arg }: any) { beforeMount(el: any, { value, arg }: any) {
if (arg === 'callback') { if (arg === 'callback') {
el.$copyCallback = value; el.$copyCallback = value;
} else { } else {
el.$copyValue = value; el.$copyValue = value;
const handler = () => { const handler = () => {
copyTextToClipboard(el.$copyValue); copyTextToClipboard(el.$copyValue);
if (el.$copyCallback) { if (el.$copyCallback) {
el.$copyCallback(el.$copyValue); el.$copyCallback(el.$copyValue);
} }
}; };
el.addEventListener('click', handler); el.addEventListener('click', handler);
el.$destroyCopy = () => el.removeEventListener('click', handler); el.$destroyCopy = () => el.removeEventListener('click', handler);
} }
} }
}; };
function copyTextToClipboard(input: string, { target = document.body } = {}) { function copyTextToClipboard(input: string, { target = document.body } = {}) {
const element = document.createElement('textarea'); const element = document.createElement('textarea');
const previouslyFocusedElement = document.activeElement as HTMLInputElement; const previouslyFocusedElement = document.activeElement as HTMLInputElement;
element.value = input; element.value = input;
// Prevent keyboard from showing on mobile // Prevent keyboard from showing on mobile
element.setAttribute('readonly', ''); element.setAttribute('readonly', '');
element.style.contain = 'strict'; element.style.contain = 'strict';
element.style.position = 'absolute'; element.style.position = 'absolute';
element.style.left = '-9999px'; element.style.left = '-9999px';
element.style.fontSize = '12pt'; // Prevent zooming on iOS element.style.fontSize = '12pt'; // Prevent zooming on iOS
const selection = document.getSelection(); const selection = document.getSelection();
let originalRange; let originalRange;
if (selection) { if (selection) {
originalRange = selection?.rangeCount > 0 && selection.getRangeAt(0); originalRange = selection?.rangeCount > 0 && selection.getRangeAt(0);
} }
target.append(element); target.append(element);
element.select(); element.select();
// Explicit selection workaround for iOS // Explicit selection workaround for iOS
element.selectionStart = 0; element.selectionStart = 0;
element.selectionEnd = input.length; element.selectionEnd = input.length;
let isSuccess = false; let isSuccess = false;
try { try {
isSuccess = document.execCommand('copy'); isSuccess = document.execCommand('copy');
} catch (err) { } catch (err) {
console.error(err); console.error(err);
} }
element.remove(); element.remove();
if (originalRange) { if (originalRange) {
selection?.removeAllRanges(); selection?.removeAllRanges();
selection?.addRange(originalRange); selection?.addRange(originalRange);
} }
// Get the focus back on the previously focused element, if any // Get the focus back on the previously focused element, if any
if (previouslyFocusedElement) { if (previouslyFocusedElement) {
previouslyFocusedElement.focus(); previouslyFocusedElement.focus();
} }
return isSuccess; return isSuccess;
} }

View File

@ -3,7 +3,7 @@ import { hasPermi, hasRoles } from './permission';
import { App } from 'vue'; import { App } from 'vue';
export default (app: App) => { export default (app: App) => {
app.directive('copyText', copyText); app.directive('copyText', copyText);
app.directive('hasPermi', hasPermi); app.directive('hasPermi', hasPermi);
app.directive('hasRoles', hasRoles); app.directive('hasRoles', hasRoles);
}; };

View File

@ -4,41 +4,41 @@ import useUserStore from '@/store/modules/user';
* 操作权限处理 * 操作权限处理
*/ */
export const hasPermi: Directive = { export const hasPermi: Directive = {
mounted(el: HTMLElement, binding: DirectiveBinding) { mounted(el: HTMLElement, binding: DirectiveBinding) {
const { permissions } = useUserStore(); const { permissions } = useUserStore();
// 「其他角色」按钮权限校验 // 「其他角色」按钮权限校验
const { value } = binding; const { value } = binding;
if (value && value instanceof Array && value.length > 0) { if (value && value instanceof Array && value.length > 0) {
const hasPermission = permissions.some((permi) => { const hasPermission = permissions.some((permi) => {
return permi === '*:*:*' || value.includes(permi); return permi === '*:*:*' || value.includes(permi);
}); });
if (!hasPermission) { if (!hasPermission) {
el.parentNode && el.parentNode.removeChild(el); el.parentNode && el.parentNode.removeChild(el);
return false; return false;
} }
} else { } else {
throw new Error("check perms! Like v-has-permi=\"['sys:user:add','sys:user:edit']\""); throw new Error("check perms! Like v-has-permi=\"['sys:user:add','sys:user:edit']\"");
} }
} }
}; };
/** /**
* 角色权限处理 * 角色权限处理
*/ */
export const hasRoles: Directive = { export const hasRoles: Directive = {
mounted(el: HTMLElement, binding: DirectiveBinding) { mounted(el: HTMLElement, binding: DirectiveBinding) {
const { value } = binding; const { value } = binding;
const { roles } = useUserStore(); const { roles } = useUserStore();
if (value && value instanceof Array && value.length > 0) { if (value && value instanceof Array && value.length > 0) {
const hasRole = roles.some((role) => { const hasRole = roles.some((role) => {
return role === 'admin' || value.includes(role); return role === 'admin' || value.includes(role);
}); });
if (!hasRole) { if (!hasRole) {
el.parentNode && el.parentNode.removeChild(el); el.parentNode && el.parentNode.removeChild(el);
return false; return false;
} }
} else { } else {
throw new Error("check roles! Like v-has-roles=\"['admin','test']\""); throw new Error("check roles! Like v-has-roles=\"['admin','test']\"");
} }
} }
}; };

View File

@ -1,15 +1,15 @@
export enum MenuTypeEnum { export enum MenuTypeEnum {
/** /**
* 目录 * 目录
*/ */
M = 'M', M = 'M',
/** /**
* 菜单 * 菜单
*/ */
C = 'C', C = 'C',
/** /**
* 按钮 * 按钮
*/ */
F = 'F' F = 'F'
} }

View File

@ -1,90 +1,90 @@
export enum HttpStatus { export enum HttpStatus {
/** /**
* 操作成功 * 操作成功
*/ */
SUCCESS = 200, SUCCESS = 200,
/** /**
* 对象创建成功 * 对象创建成功
*/ */
CREATED = 201, CREATED = 201,
/** /**
* 请求已经被接受 * 请求已经被接受
*/ */
ACCEPTED = 202, ACCEPTED = 202,
/** /**
* 操作已经执行成功,但是没有返回数据 * 操作已经执行成功,但是没有返回数据
*/ */
NO_CONTENT = 204, NO_CONTENT = 204,
/** /**
* 资源已经被移除 * 资源已经被移除
*/ */
MOVED_PERM = 301, MOVED_PERM = 301,
/** /**
* 重定向 * 重定向
*/ */
SEE_OTHER = 303, SEE_OTHER = 303,
/** /**
* 资源没有被修改 * 资源没有被修改
*/ */
NOT_MODIFIED = 304, NOT_MODIFIED = 304,
/** /**
* 参数列表错误(缺少,格式不匹配) * 参数列表错误(缺少,格式不匹配)
*/ */
PARAM_ERROR = 400, PARAM_ERROR = 400,
/** /**
* 未授权 * 未授权
*/ */
UNAUTHORIZED = 401, UNAUTHORIZED = 401,
/** /**
* 访问受限,授权过期 * 访问受限,授权过期
*/ */
FORBIDDEN = 403, FORBIDDEN = 403,
/** /**
* 资源,服务未找到 * 资源,服务未找到
*/ */
NOT_FOUND = 404, NOT_FOUND = 404,
/** /**
* 不允许的http方法 * 不允许的http方法
*/ */
BAD_METHOD = 405, BAD_METHOD = 405,
/** /**
* 资源冲突,或者资源被锁 * 资源冲突,或者资源被锁
*/ */
CONFLICT = 409, CONFLICT = 409,
/** /**
* 不支持的数据,媒体类型 * 不支持的数据,媒体类型
*/ */
UNSUPPORTED_TYPE = 415, UNSUPPORTED_TYPE = 415,
/** /**
* 系统内部错误 * 系统内部错误
*/ */
SERVER_ERROR = 500, SERVER_ERROR = 500,
/** /**
* 接口未实现 * 接口未实现
*/ */
NOT_IMPLEMENTED = 501, NOT_IMPLEMENTED = 501,
/** /**
* 服务不可用,过载或者维护 * 服务不可用,过载或者维护
*/ */
BAD_GATEWAY = 502, BAD_GATEWAY = 502,
/** /**
* 网关超时 * 网关超时
*/ */
GATEWAY_TIMEOUT = 504, GATEWAY_TIMEOUT = 504,
/** /**
* 未知错误 * 未知错误
*/ */
UNKNOWN_ERROR = 520, UNKNOWN_ERROR = 520,
/** /**
* 服务未知错误 * 服务未知错误
*/ */
SERVICE_ERROR = 521, SERVICE_ERROR = 521,
/** /**
* 数据库未知错误 * 数据库未知错误
*/ */
DATABASE_ERROR = 522, DATABASE_ERROR = 522,
/** /**
* 系统警告消息 * 系统警告消息
*/ */
WARN = 601 WARN = 601
} }

View File

@ -1,16 +1,16 @@
export enum SettingTypeEnum { export enum SettingTypeEnum {
TITLE = 'title', TITLE = 'title',
THEME = 'theme', THEME = 'theme',
SIDE_THEME = 'sideTheme', SIDE_THEME = 'sideTheme',
SHOW_SETTINGS = 'showSettings', SHOW_SETTINGS = 'showSettings',
TOP_NAV = 'topNav', TOP_NAV = 'topNav',
TAGS_VIEW = 'tagsView', TAGS_VIEW = 'tagsView',
FIXED_HEADER = 'fixedHeader', FIXED_HEADER = 'fixedHeader',
SIDEBAR_LOGO = 'sidebarLogo', SIDEBAR_LOGO = 'sidebarLogo',
DYNAMIC_TITLE = 'dynamicTitle', DYNAMIC_TITLE = 'dynamicTitle',
ANIMATION_ENABLE = 'animationEnable', ANIMATION_ENABLE = 'animationEnable',
LAYOUT = 'layout', LAYOUT = 'layout',
DARK = 'dark', DARK = 'dark',
LAYOUT_SETTING = 'layout-setting' LAYOUT_SETTING = 'layout-setting'
} }

View File

@ -1,4 +1,4 @@
export enum ThemeEnum { export enum ThemeEnum {
DARK = 'theme-dark', DARK = 'theme-dark',
LIGHT = 'theme-light' LIGHT = 'theme-light'
} }

View File

@ -1,25 +1,25 @@
export default { export default {
// 路由国际化 // 路由国际化
route: { route: {
dashboard: 'Dashboard', dashboard: 'Dashboard',
document: 'Document' document: 'Document'
}, },
// 登录页面国际化 // 登录页面国际化
login: { login: {
title: 'vue3-element-admin', title: 'vue3-element-admin',
username: 'Username', username: 'Username',
password: 'Password', password: 'Password',
login: 'Login', login: 'Login',
code: 'Verification Code', code: 'Verification Code',
copyright: '', copyright: '',
icp: '', icp: '',
thirdPartyLogin: 'third-party login' thirdPartyLogin: 'third-party login'
}, },
// 导航栏国际化 // 导航栏国际化
navbar: { navbar: {
dashboard: 'Dashboard', dashboard: 'Dashboard',
logout: 'Logout', logout: 'Logout',
document: 'Document', document: 'Document',
gitee: 'Gitee' gitee: 'Gitee'
} }
}; };

View File

@ -6,12 +6,12 @@ import enLocale from './en';
import zhCnLocale from './zh-cn'; import zhCnLocale from './zh-cn';
const messages = { const messages = {
'zh-cn': { 'zh-cn': {
...zhCnLocale ...zhCnLocale
}, },
en: { en: {
...enLocale ...enLocale
} }
}; };
/** /**
@ -20,26 +20,26 @@ const messages = {
* @returns zh-cn|en ... * @returns zh-cn|en ...
*/ */
export const getLanguage = () => { export const getLanguage = () => {
// 本地缓存获取 // 本地缓存获取
let language = localStorage.getItem('language'); let language = localStorage.getItem('language');
if (language) { if (language) {
return language; return language;
} }
// 浏览器使用语言 // 浏览器使用语言
language = navigator.language.toLowerCase(); language = navigator.language.toLowerCase();
const locales = Object.keys(messages); const locales = Object.keys(messages);
for (const locale of locales) { for (const locale of locales) {
if (language.indexOf(locale) > -1) { if (language.indexOf(locale) > -1) {
return locale; return locale;
} }
} }
return 'zh-cn'; return 'zh-cn';
}; };
const i18n = createI18n({ const i18n = createI18n({
legacy: false, legacy: false,
locale: getLanguage(), locale: getLanguage(),
messages: messages messages: messages
}); });
export default i18n; export default i18n;

View File

@ -1,24 +1,24 @@
export default { export default {
// 路由国际化 // 路由国际化
route: { route: {
dashboard: '首页', dashboard: '首页',
document: '项目文档' document: '项目文档'
}, },
// 登录页面国际化 // 登录页面国际化
login: { login: {
title: 'vue3-element-admin', title: 'vue3-element-admin',
username: '用户名', username: '用户名',
password: '密码', password: '密码',
login: '登 录', login: '登 录',
code: '请输入验证码', code: '请输入验证码',
copyright: '', copyright: '',
icp: '', icp: '',
thirdPartyLogin: '第三方登录' thirdPartyLogin: '第三方登录'
}, },
navbar: { navbar: {
dashboard: '首页', dashboard: '首页',
logout: '注销', logout: '注销',
document: '项目文档', document: '项目文档',
gitee: '码云' gitee: '码云'
} }
}; };

View File

@ -1,6 +1,19 @@
<template>
<section class="app-main">
<router-view v-slot="{ Component, route }">
<transition :enter-active-class="animante" mode="out-in">
<keep-alive :include="tagsViewStore.cachedViews">
<component v-if="!route.meta.link" :is="Component" :key="route.path" />
</keep-alive>
</transition>
</router-view>
<iframe-toggle />
</section>
</template>
<script lang="ts"> <script lang="ts">
export default { export default {
name: 'AppMin' name: 'AppMin'
} }
</script> </script>
@ -16,28 +29,15 @@ const tagsViewStore = useTagsViewStore();
const animante = ref<string>(''); const animante = ref<string>('');
const animationEnable = ref(useSettingsStore().animationEnable); const animationEnable = ref(useSettingsStore().animationEnable);
watch(()=> useSettingsStore().animationEnable, (val) => { watch(()=> useSettingsStore().animationEnable, (val) => {
animationEnable.value = val; animationEnable.value = val;
if (val) { if (val) {
animante.value = proxy?.animate.animateList[Math.round(Math.random() * proxy?.animate.animateList.length)] as string; animante.value = proxy?.animate.animateList[Math.round(Math.random() * proxy?.animate.animateList.length)] as string;
} else { } else {
animante.value = proxy?.animate.defaultAnimate as string; animante.value = proxy?.animate.defaultAnimate as string;
} }
}, { immediate: true }); }, { immediate: true });
</script> </script>
<template>
<section class="app-main">
<router-view v-slot="{ Component, route }">
<transition :enter-active-class="animante" mode="out-in">
<keep-alive :include="tagsViewStore.cachedViews">
<component v-if="!route.meta.link" :is="Component" :key="route.path" />
</keep-alive>
</transition>
</router-view>
<iframe-toggle />
</section>
</template>
<style lang="scss" scoped> <style lang="scss" scoped>
.app-main { .app-main {
/* 50= navbar 50 */ /* 50= navbar 50 */

View File

@ -7,13 +7,13 @@ const tagsViewStore = useTagsViewStore()
</script> </script>
<template> <template>
<transition-group name="fade-transform" mode="out-in"> <transition-group name="fade-transform" mode="out-in">
<inner-link <inner-link
v-for="(item, index) in tagsViewStore.iframeViews" v-for="(item, index) in tagsViewStore.iframeViews"
:key="item.path" :key="item.path"
:iframeId="'iframe' + index" :iframeId="'iframe' + index"
v-show="route.path === item.path" v-show="route.path === item.path"
:src="item.meta ? item.meta.link : ''" :src="item.meta ? item.meta.link : ''"
></inner-link> ></inner-link>
</transition-group> </transition-group>
</template> </template>

View File

@ -1,18 +1,18 @@
<template>
<div :style="'height:' + height">
<iframe :id="iframeId" style="width: 100%; height: 100%" :src="src" frameborder="no"></iframe>
</div>
</template>
<script setup lang="ts"> <script setup lang="ts">
const props = defineProps({ const props = defineProps({
src: { src: {
type: String, type: String,
default: "/" default: "/"
}, },
iframeId: { iframeId: {
type: String type: String
} }
}); });
const height = ref(document.documentElement.clientHeight - 94.5 + "px"); const height = ref(document.documentElement.clientHeight - 94.5 + "px");
</script> </script>
<template>
<div :style="'height:' + height">
<iframe :id="iframeId" style="width: 100%; height: 100%" :src="src" frameborder="no"></iframe>
</div>
</template>

Some files were not shown because too many files have changed in this diff Show More