Browse Source

chore: update deps

main
刘凯 11 months ago
parent
commit
ed99d3ce76
  1. 6
      build/utils.ts
  2. 1
      build/vite/plugin/html.ts
  3. 3
      eslint.config.js
  4. 88
      package.json
  5. 5380
      pnpm-lock.yaml
  6. 1
      public/resource/tinymce/langs/en.js
  7. 1
      public/resource/tinymce/langs/zh_CN.js
  8. 2
      src/components/Container/src/LazyContainer.vue
  9. 8
      src/components/Container/src/collapse/CollapseContainer.vue
  10. 2
      src/components/ContextMenu/src/createContextMenu.ts
  11. 4
      src/components/CronTab/index.ts
  12. 360
      src/components/CronTab/src/CronTabInner.vue
  13. 55
      src/components/CronTab/src/CronTabInput.vue
  14. 18
      src/components/CronTab/src/CronTabModal.vue
  15. 10
      src/components/CronTab/src/cron.data.ts
  16. 101
      src/components/CronTab/src/tabs/DayUI.vue
  17. 69
      src/components/CronTab/src/tabs/HourUI.vue
  18. 69
      src/components/CronTab/src/tabs/MinuteUI.vue
  19. 69
      src/components/CronTab/src/tabs/MonthUI.vue
  20. 69
      src/components/CronTab/src/tabs/SecondUI.vue
  21. 135
      src/components/CronTab/src/tabs/WeekUI.vue
  22. 55
      src/components/CronTab/src/tabs/YearUI.vue
  23. 204
      src/components/CronTab/src/tabs/useTabMixin.ts
  24. 50
      src/components/CronTab/src/validator.ts
  25. 2
      src/components/Description/src/typing.ts
  26. 2
      src/components/EllipsisText/src/_utils.ts
  27. 2
      src/components/Form/src/components/FileUpload.vue
  28. 10
      src/components/Form/src/components/FormItem.vue
  29. 5
      src/components/Form/src/hooks/useFormEvents.ts
  30. 4
      src/components/Form/src/types/index.ts
  31. 2
      src/components/Markdown/src/Markdown.vue
  32. 2
      src/components/Markdown/src/MarkdownViewer.vue
  33. 6
      src/components/Modal/src/components/ModalWrapper.vue
  34. 5
      src/components/Preview/src/Functional.vue
  35. 19
      src/components/Table/src/BasicTable.vue
  36. 4
      src/components/Table/src/components/HeaderCell.vue
  37. 2
      src/components/Table/src/components/editable/EditableCell.vue
  38. 3
      src/components/Table/src/components/editable/helper.ts
  39. 2
      src/components/Table/src/hooks/useColumns.ts
  40. 2
      src/components/Table/src/hooks/useRender.ts
  41. 1
      src/components/Table/src/hooks/useTable.ts
  42. 1
      src/components/Table/src/props.ts
  43. 2
      src/components/Table/src/types/column.ts
  44. 9
      src/components/Table/src/types/table.ts
  45. 28
      src/components/Tree/src/BasicTree.vue
  46. 2
      src/hooks/setting/index.ts
  47. 2
      src/hooks/web/useContentHeight.ts
  48. 18
      src/hooks/web/useMessage.tsx
  49. 2
      src/hooks/web/usePermission.ts
  50. 3
      src/layouts/default/header/MultipleHeader.vue
  51. 18
      src/layouts/default/menu/index.vue
  52. 4
      src/logics/error-handle/index.ts
  53. 4
      src/router/guard/permissionGuard.ts
  54. 2
      src/router/helper/menuHelper.ts
  55. 2
      src/store/modules/lock.ts
  56. 3
      src/store/modules/multipleTab.ts
  57. 2
      src/store/modules/permission.ts
  58. 4
      src/store/modules/user.ts
  59. 2
      src/utils/cache/storageCache.ts
  60. 6
      src/utils/cipher.ts
  61. 2
      src/utils/color.ts
  62. 22
      src/utils/dateUtil.ts
  63. 2
      src/utils/domUtils.ts
  64. 2
      src/utils/env.ts
  65. 2
      src/utils/file/download.ts
  66. 3
      src/utils/http/axios/Axios.ts
  67. 6
      src/utils/index.ts
  68. 2
      src/utils/is.ts
  69. 11
      src/utils/mitt.ts
  70. 12
      src/utils/props.ts
  71. 2
      src/utils/tree.ts
  72. 2
      vite.config.ts

6
build/utils.ts

@ -34,7 +34,7 @@ export function wrapperEnv(envConf: Recordable): ViteEnv {
try {
realName = JSON.parse(realName.replace(/'/g, '"'))
}
catch (error) {
catch {
realName = ''
}
}
@ -71,8 +71,8 @@ export async function getEnvConfig(
match = 'VITE_GLOB_',
confFiles = getConfFiles(),
): Promise<{
[key: string]: string
}> {
[key: string]: string
}> {
let envConfig = {}
for (const confFile of confFiles) {

1
build/vite/plugin/html.ts

@ -8,7 +8,6 @@ import { createHtmlPlugin } from 'vite-plugin-html'
export function configHtmlPlugin({ isBuild }: { isBuild: boolean }) {
const htmlPlugin: PluginOption[] = createHtmlPlugin({
minify: isBuild,
viteNext: true,
})
return htmlPlugin
}

3
eslint.config.js

@ -10,6 +10,9 @@ export default antfu(
'vue/component-name-in-template-casing': 'off',
'vue/require-toggle-inside-transition': 'off',
'ts/no-use-before-define': 'off',
'no-unused-expressions': 'off',
'@typescript-eslint/no-unused-expressions': 'off',
'regexp/no-unused-capturing-group': 'off',
},
},
unocss.configs.flat,

88
package.json

@ -24,84 +24,84 @@
"release": "bumpp -x \"pnpm run changelog\" --all"
},
"dependencies": {
"@ant-design/colors": "^7.0.2",
"@ant-design/colors": "^7.1.0",
"@ant-design/icons-vue": "^7.0.1",
"@codemirror/commands": "^6.3.3",
"@codemirror/commands": "^6.6.0",
"@codemirror/lang-javascript": "^6.2.2",
"@codemirror/lang-json": "^6.0.1",
"@codemirror/state": "^6.4.1",
"@codemirror/theme-one-dark": "^6.1.2",
"@codemirror/view": "^6.25.1",
"@vueuse/core": "^10.6.1",
"@codemirror/view": "^6.28.4",
"@vueuse/core": "^10.11.0",
"@zxcvbn-ts/core": "^3.0.4",
"ant-design-vue": "~4.0.8",
"axios": "^1.6.4",
"ant-design-vue": "^4.2.3",
"axios": "^1.7.2",
"codemirror": "^6.0.1",
"cron-parser": "^4.9.0",
"cropperjs": "^1.6.1",
"cropperjs": "^1.6.2",
"crypto-js": "^4.2.0",
"dayjs": "^1.11.10",
"echarts": "^5.4.3",
"dayjs": "^1.11.11",
"echarts": "^5.5.1",
"lodash-es": "^4.17.21",
"nprogress": "^0.2.0",
"path-to-regexp": "^6.2.1",
"path-to-regexp": "^6.2.2",
"pinia": "^2.1.7",
"pinia-plugin-persistedstate": "^3.2.1",
"print-js": "^1.6.0",
"qs": "^6.11.2",
"qs": "^6.12.3",
"resize-observer-polyfill": "^1.5.1",
"sortablejs": "^1.15.1",
"sortablejs": "^1.15.2",
"tinymce": "^5.10.9",
"vditor": "^3.9.8",
"vite-plugin-html": "^3.2.1",
"vue": "~3.3.8",
"vue-i18n": "^9.9.0",
"vue-json-pretty": "^2.3.0",
"vue-router": "^4.2.5",
"vue-types": "^5.1.1",
"vditor": "^3.10.4",
"vite-plugin-html": "^3.2.2",
"vue": "^3.4.31",
"vue-i18n": "^9.13.1",
"vue-json-pretty": "^2.4.0",
"vue-router": "^4.4.0",
"vue-types": "^5.1.3",
"vuedraggable": "^4.1.0",
"xlsx": "^0.18.5"
},
"devDependencies": {
"@antfu/eslint-config": "^2.6.2",
"@iconify/json": "^2.2.164",
"@antfu/eslint-config": "^2.22.3",
"@iconify/json": "^2.2.228",
"@types/codemirror": "^5.60.15",
"@types/crypto-js": "^4.2.1",
"@types/crypto-js": "^4.2.2",
"@types/fs-extra": "^11.0.4",
"@types/lodash-es": "^4.17.12",
"@types/node": "^20.11.0",
"@types/node": "^20.14.10",
"@types/nprogress": "^0.2.3",
"@types/qs": "^6.9.11",
"@types/sortablejs": "^1.15.5",
"@unocss/eslint-config": "^0.58.3",
"@types/qs": "^6.9.15",
"@types/sortablejs": "^1.15.8",
"@unocss/eslint-config": "^0.58.9",
"@vitejs/plugin-vue": "^4.6.2",
"@vitejs/plugin-vue-jsx": "^3.1.0",
"@vue/compiler-sfc": "^3.4.10",
"bumpp": "^9.2.1",
"@vue/compiler-sfc": "^3.4.31",
"bumpp": "^9.4.1",
"cross-env": "^7.0.3",
"dotenv": "^16.3.1",
"eslint": "^8.56.0",
"esno": "^4.0.0",
"dotenv": "^16.4.5",
"eslint": "^8.57.0",
"esno": "^4.7.0",
"fs-extra": "^11.2.0",
"inquirer": "^9.2.12",
"inquirer": "^9.3.5",
"less": "^4.2.0",
"lint-staged": "^15.2.0",
"picocolors": "^1.0.0",
"postcss": "^8.4.33",
"postcss-html": "^1.5.0",
"lint-staged": "^15.2.7",
"picocolors": "^1.0.1",
"postcss": "^8.4.39",
"postcss-html": "^1.7.0",
"postcss-less": "^6.0.0",
"rimraf": "^5.0.5",
"rimraf": "^5.0.9",
"rollup-plugin-visualizer": "^5.12.0",
"simple-git-hooks": "^2.9.0",
"terser": "^5.26.0",
"typescript": "^5.3.3",
"unocss": "^0.58.3",
"vite": "^4.5.1",
"simple-git-hooks": "^2.11.1",
"terser": "^5.31.2",
"typescript": "^5.5.3",
"unocss": "^0.61.3",
"vite": "^5.3.3",
"vite-plugin-compression": "^0.5.1",
"vite-plugin-pwa": "^0.17.4",
"vite-plugin-pwa": "^0.17.5",
"vite-plugin-svg-icons": "^2.0.1",
"vite-vue-plugin-html": "^1.0.5",
"vue-tsc": "^1.8.27"
"vue-tsc": "^2.0.26"
},
"simple-git-hooks": {
"pre-commit": "pnpm lint-staged && pnpm type:check",

5380
pnpm-lock.yaml

File diff suppressed because it is too large Load Diff

1
public/resource/tinymce/langs/en.js

@ -1,3 +1,4 @@
// eslint-disable-next-line no-undef
tinymce.addI18n('es', {
'Redo': 'Rehacer',
'Undo': 'Deshacer',

1
public/resource/tinymce/langs/zh_CN.js

@ -1,3 +1,4 @@
// eslint-disable-next-line no-undef
tinymce.addI18n('zh_CN', {
'Redo': '\u91CD\u505A',
'Undo': '\u64A4\u9500',

2
src/components/Container/src/LazyContainer.vue

@ -112,7 +112,7 @@ function initIntersectionObserver() {
root: toRef(props, 'viewport'),
})
}
catch (e) {
catch {
init()
}
}

8
src/components/Container/src/collapse/CollapseContainer.vue

@ -72,12 +72,12 @@ export default defineComponent({
<CollapseTransition enable={props.canExpan}>
{props.loading
? (
<Skeleton active={props.loading} />
<Skeleton active={props.loading} />
)
: (
<div class={`${prefixCls}__body`} v-show={show.value}>
{slots.default?.()}
</div>
<div class={`${prefixCls}__body`} v-show={show.value}>
{slots.default?.()}
</div>
)}
</CollapseTransition>
</div>

2
src/components/ContextMenu/src/createContextMenu.ts

@ -49,7 +49,7 @@ export const createContextMenu = function (options: CreateContextOptions) {
try {
dom && body.removeChild(dom)
}
catch (error) {}
catch {}
})
body.removeEventListener('click', handleClick)
body.removeEventListener('scroll', handleClick)

4
src/components/CronTab/index.ts

@ -1,4 +0,0 @@
export { default as CronTab } from './src/CronTabInput.vue'
export { default as CronTabInner } from './src/CronTabInner.vue'
export { default as CronTabModal } from './src/CronTabModal.vue'
export { default as CronValidator } from './src/validator'

360
src/components/CronTab/src/CronTabInner.vue

@ -1,360 +0,0 @@
<script lang="ts" setup>
import { computed, provide, reactive, ref, watch } from 'vue'
import { Col, Divider, Input, Row, TabPane, Tabs, Textarea, Tooltip } from 'ant-design-vue'
import CronParser from 'cron-parser'
import SecondUI from './tabs/SecondUI.vue'
import MinuteUI from './tabs/MinuteUI.vue'
import HourUI from './tabs/HourUI.vue'
import DayUI from './tabs/DayUI.vue'
import MonthUI from './tabs/MonthUI.vue'
import WeekUI from './tabs/WeekUI.vue'
import YearUI from './tabs/YearUI.vue'
import { cronEmits, cronProps } from './cron.data'
import { useDesign } from '@/hooks/web/useDesign'
import { dateFormat } from '@/utils/dateUtil'
import { simpleDebounce } from '@/utils'
const props = defineProps({ ...cronProps })
const emit = defineEmits([...cronEmits])
const { prefixCls } = useDesign('cron-inner')
provide('prefixCls', prefixCls)
const activeKey = ref(props.hideSecond ? 'minute' : 'second')
const second = ref('*')
const minute = ref('*')
const hour = ref('*')
const day = ref('*')
const month = ref('*')
const week = ref('?')
const year = ref('*')
const inputValues = reactive({
second: '',
minute: '',
hour: '',
day: '',
month: '',
week: '',
year: '',
cron: '',
})
const preTimeList = ref('执行预览,会忽略年份参数。')
// cron
const cronValueInner = computed(() => {
const result: string[] = []
if (!props.hideSecond)
result.push(second.value ? second.value : '*')
result.push(minute.value ? minute.value : '*')
result.push(hour.value ? hour.value : '*')
result.push(day.value ? day.value : '*')
result.push(month.value ? month.value : '*')
result.push(week.value ? week.value : '?')
if (!props.hideYear && !props.hideSecond)
result.push(year.value ? year.value : '*')
return result.join(' ')
})
//
const cronValueNoYear = computed(() => {
const v = cronValueInner.value
if (props.hideYear || props.hideSecond)
return v
const vs = v.split(' ')
if (vs.length >= 6) {
// Quartz
vs[5] = convertWeekToQuartz(vs[5])
}
return vs.slice(0, vs.length - 1).join(' ')
})
const calTriggerList = simpleDebounce(calTriggerListInner, 500)
watch(
() => props.value,
(newVal) => {
if (newVal === cronValueInner.value)
return
formatValue()
},
)
watch(cronValueInner, (newValue) => {
calTriggerList()
emitValue(newValue)
assignInput()
})
assignInput()
formatValue()
calTriggerListInner()
function assignInput() {
inputValues.second = second.value
inputValues.minute = minute.value
inputValues.hour = hour.value
inputValues.day = day.value
inputValues.month = month.value
inputValues.week = week.value
inputValues.year = year.value
inputValues.cron = cronValueInner.value
}
function formatValue() {
if (!props.value)
return
const values = props.value.split(' ').filter(item => !!item)
if (!values || values.length <= 0)
return
let i = 0
if (!props.hideSecond)
second.value = values[i++]
if (values.length > i)
minute.value = values[i++]
if (values.length > i)
hour.value = values[i++]
if (values.length > i)
day.value = values[i++]
if (values.length > i)
month.value = values[i++]
if (values.length > i)
week.value = values[i++]
if (values.length > i)
year.value = values[i]
assignInput()
}
// Quartz
// 1 = 2 = 3 = 4 = 5 = 6 = 7 =
function convertWeekToQuartz(week: string) {
const convert = (v: string) => {
if (v === '0')
return '1'
if (v === '1')
return '0'
return (Number.parseInt(v) - 1).toString()
}
// 1-7 or 1/7
const patten1 = /^([0-7])([-/])([0-7])$/
// 1,4,7
const patten2 = /^([0-7])(,[0-7])+$/
if (/^[0-7]$/.test(week)) {
return convert(week)
}
else if (patten1.test(week)) {
return week.replace(patten1, (_$0, before, separator, after) => {
if (separator === '/')
return convert(before) + separator + after
else
return convert(before) + separator + convert(after)
})
}
else if (patten2.test(week)) {
return week
.split(',')
.map(v => convert(v))
.join(',')
}
return week
}
function calTriggerListInner() {
//
if (props.remote) {
props.remote(cronValueInner.value, +new Date(), (v) => {
preTimeList.value = v
})
return
}
const format = 'yyyy-MM-dd hh:mm:ss'
const options = {
currentDate: dateFormat(new Date(), format),
}
const iter = CronParser.parseExpression(cronValueNoYear.value, options)
const result: string[] = []
for (let i = 1; i <= 10; i++)
result.push(dateFormat(new Date(iter.next() as any), format))
preTimeList.value = result.length > 0 ? result.join('\n') : '无执行时间'
}
function onInputBlur() {
second.value = inputValues.second
minute.value = inputValues.minute
hour.value = inputValues.hour
day.value = inputValues.day
month.value = inputValues.month
week.value = inputValues.week
year.value = inputValues.year
}
function onInputCronBlur(event) {
emitValue(event.target.value)
}
function emitValue(value) {
emit('change', value)
emit('update:value', value)
}
</script>
<template>
<div :class="`${prefixCls}`">
<div class="content">
<Tabs v-model:activeKey="activeKey" size="small">
<TabPane v-if="!hideSecond" key="second" tab="秒">
<SecondUI v-model:value="second" :disabled="disabled" />
</TabPane>
<TabPane key="minute" tab="分">
<MinuteUI v-model:value="minute" :disabled="disabled" />
</TabPane>
<TabPane key="hour" tab="时">
<HourUI v-model:value="hour" :disabled="disabled" />
</TabPane>
<TabPane key="day" tab="日">
<DayUI v-model:value="day" :week="week" :disabled="disabled" />
</TabPane>
<TabPane key="month" tab="月">
<MonthUI v-model:value="month" :disabled="disabled" />
</TabPane>
<TabPane key="week" tab="周">
<WeekUI v-model:value="week" :day="day" :disabled="disabled" />
</TabPane>
<TabPane v-if="!hideYear && !hideSecond" key="year" tab="年">
<YearUI v-model:value="year" :disabled="disabled" />
</TabPane>
</Tabs>
<Divider />
<!-- 执行时间预览 -->
<Row :gutter="8">
<Col :span="18" style="margin-top: 22px">
<Row :gutter="8">
<Col :span="8" style="margin-bottom: 12px">
<Input v-model:value="inputValues.second" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'second'"></span>
</template>
</Input>
</Col>
<Col :span="8" style="margin-bottom: 12px">
<Input v-model:value="inputValues.minute" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'minute'"></span>
</template>
</Input>
</Col>
<Col :span="8" style="margin-bottom: 12px">
<Input v-model:value="inputValues.hour" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'hour'"></span>
</template>
</Input>
</Col>
<Col :span="8" style="margin-bottom: 12px">
<Input v-model:value="inputValues.day" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'day'"></span>
</template>
</Input>
</Col>
<Col :span="8" style="margin-bottom: 12px">
<Input v-model:value="inputValues.month" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'month'"></span>
</template>
</Input>
</Col>
<Col :span="8" style="margin-bottom: 12px">
<Input v-model:value="inputValues.week" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'week'"></span>
</template>
</Input>
</Col>
<Col :span="8">
<Input v-model:value="inputValues.year" @blur="onInputBlur">
<template #addonBefore>
<span class="allow-click" @click="activeKey = 'year'"></span>
</template>
</Input>
</Col>
<Col :span="16">
<Input v-model:value="inputValues.cron" @blur="onInputCronBlur">
<template #addonBefore>
<Tooltip title="Cron表达式">
</Tooltip>
</template>
</Input>
</Col>
</Row>
</Col>
<Col :span="6">
<div>近十次执行时间不含年</div>
<Textarea :value="preTimeList" :rows="5" />
</Col>
</Row>
</div>
</div>
</template>
<style lang="less">
@prefix-cls: ~'@{namespace}-cron-inner';
.@{prefix-cls} {
.content {
.ant-checkbox-wrapper + .ant-checkbox-wrapper {
margin-left: 0;
}
}
&-config-list {
margin: 0 10px 10px;
text-align: left;
.item {
margin-top: 5px;
font-size: 14px;
span {
padding: 0 2px;
}
}
.choice {
padding: 5px 8px;
}
.w60 {
width: 60px;
min-width: 60px;
}
.w80 {
width: 80px;
min-width: 80px;
}
.list {
margin: 0 20px;
}
.list-check-item {
width: 4em;
padding: 1px 3px;
}
.list-cn .list-check-item {
width: 5em;
}
.tip-info {
color: #999;
}
}
.allow-click {
cursor: pointer;
}
}
</style>

55
src/components/CronTab/src/CronTabInput.vue

@ -1,55 +0,0 @@
<script lang="ts" setup>
import { ref, watch } from 'vue'
import { Input } from 'ant-design-vue'
import CronTabModal from './CronTabModal.vue'
import { cronEmits, cronProps } from './cron.data'
import { useModal } from '@/components/Modal'
import { propTypes } from '@/utils/propTypes'
const props = defineProps({
...cronProps,
placeholder: propTypes.string.def('请输入cron表达式'),
exeStartTime: propTypes.oneOfType([propTypes.number, propTypes.string, propTypes.object]).def(0),
})
const emit = defineEmits([...cronEmits])
const [registerModal, { openModal }] = useModal()
const editCronValue = ref(props.value)
watch(
() => props.value,
(newVal) => {
if (newVal !== editCronValue.value)
editCronValue.value = newVal
},
)
watch(editCronValue, (newVal) => {
emit('change', newVal)
emit('update:value', newVal)
})
function showConfigModal() {
if (!props.disabled)
openModal()
}
</script>
<template>
<div>
<Input v-model:value="editCronValue" :placeholder="placeholder" :disabled="disabled">
<template #addonAfter>
<a class="cursor-pointer" :disabled="disabled ? 'disabled' : null" @click="showConfigModal">
<span class="i-ant-design:setting-outlined relative right-0.5 top-0.25" />
<span>选择</span>
</a>
</template>
</Input>
<CronTabModal
v-model:value="editCronValue"
:exe-start-time="exeStartTime"
:hide-year="hideYear"
:remote="remote"
:hide-second="hideSecond"
@register="registerModal"
/>
</div>
</template>

18
src/components/CronTab/src/CronTabModal.vue

@ -1,18 +0,0 @@
<script lang="ts" setup>
import CronTab from './CronTabInner.vue'
import { BasicModal, useModalInner } from '@/components/Modal'
defineOptions({ name: 'CronTabModal', inheritAttrs: false })
const [registerModal, { closeModal }] = useModalInner()
function onOk() {
closeModal()
}
</script>
<template>
<BasicModal title="Cron表达式" width="800px" @register="registerModal" @ok="onOk">
<CronTab v-bind="$attrs" />
</BasicModal>
</template>

10
src/components/CronTab/src/cron.data.ts

@ -1,10 +0,0 @@
import { propTypes } from '@/utils/propTypes'
export const cronEmits = ['change', 'update:value']
export const cronProps = {
value: propTypes.string.def(''),
disabled: propTypes.bool.def(false),
hideSecond: propTypes.bool.def(false),
hideYear: propTypes.bool.def(false),
remote: propTypes.func,
}

101
src/components/CronTab/src/tabs/DayUI.vue

@ -1,101 +0,0 @@
<script lang="ts">
import { computed, defineComponent, watch } from 'vue'
import { Checkbox, Input, Radio } from 'ant-design-vue'
import { TypeEnum, useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
export default defineComponent({
name: 'DayUI',
components: { AInput: Input, Checkbox, CheckboxGroup: Checkbox.Group, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '*',
props: {
week: { type: String, default: '?' },
},
}),
emits: useTabEmits(),
setup(props, context) {
const disabledChoice = computed(() => {
return (props.week && props.week !== '?') || props.disabled
})
const setup = useTabSetup(props, context, {
defaultValue: '*',
valueWork: 1,
minValue: 1,
maxValue: 31,
valueRange: { start: 1, end: 31 },
valueLoop: { start: 1, interval: 1 },
disabled: disabledChoice,
})
const typeWorkAttrs = computed(() => ({
disabled: setup.type.value !== TypeEnum.work || props.disabled || disabledChoice.value,
...setup.inputNumberAttrs.value,
}))
watch(
() => props.week,
() => {
setup.updateValue(disabledChoice.value ? '?' : setup.computeValue.value)
},
)
return { ...setup, typeWorkAttrs }
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.unset" v-bind="beforeRadioAttrs">
不设置
</Radio>
<span class="tip-info">日和周只能设置其中之一</span>
</div>
<div class="item">
<Radio :value="TypeEnum.every" v-bind="beforeRadioAttrs">
每日
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<AInput v-model:value="valueRange.start" type="number" v-bind="typeRangeAttrs" />
<span> </span>
<AInput v-model:value="valueRange.end" type="number" v-bind="typeRangeAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<AInput v-model:value="valueLoop.start" type="number" class="w-4" v-bind="typeLoopAttrs" />
<span> 日开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" v-bind="typeLoopAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.last" v-bind="beforeRadioAttrs">
最后一日
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.specify" v-bind="beforeRadioAttrs">
指定
</Radio>
<div class="list">
<CheckboxGroup v-model:value="valueList">
<template v-for="i in specifyRange" :key="i">
<Checkbox :value="i" v-bind="typeSpecifyAttrs">
{{ i }}
</Checkbox>
</template>
</CheckboxGroup>
</div>
</div>
</RadioGroup>
</div>
</template>

69
src/components/CronTab/src/tabs/HourUI.vue

@ -1,69 +0,0 @@
<script lang="ts">
import { defineComponent } from 'vue'
import { Checkbox, Input, Radio } from 'ant-design-vue'
import { useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
export default defineComponent({
name: 'HourUI',
components: { AInput: Input, Checkbox, CheckboxGroup: Checkbox.Group, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '*',
}),
emits: useTabEmits(),
setup(props, context) {
return useTabSetup(props, context, {
defaultValue: '*',
minValue: 0,
maxValue: 23,
valueRange: { start: 0, end: 23 },
valueLoop: { start: 0, interval: 1 },
})
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.every" v-bind="beforeRadioAttrs">
每时
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<AInput v-model:value="valueRange.start" type="number" v-bind="typeRangeAttrs" />
<span> </span>
<AInput v-model:value="valueRange.end" type="number" v-bind="typeRangeAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<AInput v-model:value="valueLoop.start" type="number" v-bind="typeLoopAttrs" />
<span> 时开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" v-bind="typeLoopAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.specify" v-bind="beforeRadioAttrs">
指定
</Radio>
<div class="list">
<CheckboxGroup v-model:value="valueList">
<template v-for="i in specifyRange" :key="i">
<Checkbox :value="i" v-bind="typeSpecifyAttrs">
{{ i }}
</Checkbox>
</template>
</CheckboxGroup>
</div>
</div>
</RadioGroup>
</div>
</template>

69
src/components/CronTab/src/tabs/MinuteUI.vue

@ -1,69 +0,0 @@
<script lang="ts">
import { defineComponent } from 'vue'
import { Checkbox, Input, Radio } from 'ant-design-vue'
import { useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
export default defineComponent({
name: 'MinuteUI',
components: { AInput: Input, Checkbox, CheckboxGroup: Checkbox.Group, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '*',
}),
emits: useTabEmits(),
setup(props, context) {
return useTabSetup(props, context, {
defaultValue: '*',
minValue: 0,
maxValue: 59,
valueRange: { start: 0, end: 59 },
valueLoop: { start: 0, interval: 1 },
})
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.every" v-bind="beforeRadioAttrs">
每分
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<AInput v-model:value="valueRange.start" type="number" v-bind="typeRangeAttrs" />
<span> </span>
<AInput v-model:value="valueRange.end" type="number" v-bind="typeRangeAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<AInput v-model:value="valueLoop.start" type="number" v-bind="typeLoopAttrs" />
<span> 分开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" v-bind="typeLoopAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.specify" v-bind="beforeRadioAttrs">
指定
</Radio>
<div class="list">
<CheckboxGroup v-model:value="valueList">
<template v-for="i in specifyRange" :key="i">
<Checkbox :value="i" v-bind="typeSpecifyAttrs">
{{ i }}
</Checkbox>
</template>
</CheckboxGroup>
</div>
</div>
</RadioGroup>
</div>
</template>

69
src/components/CronTab/src/tabs/MonthUI.vue

@ -1,69 +0,0 @@
<script lang="ts">
import { defineComponent } from 'vue'
import { Checkbox, Input, Radio } from 'ant-design-vue'
import { useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
export default defineComponent({
name: 'MonthUI',
components: { AInput: Input, Checkbox, CheckboxGroup: Checkbox.Group, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '*',
}),
emits: useTabEmits(),
setup(props, context) {
return useTabSetup(props, context, {
defaultValue: '*',
minValue: 1,
maxValue: 12,
valueRange: { start: 1, end: 12 },
valueLoop: { start: 1, interval: 1 },
})
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.every" v-bind="beforeRadioAttrs">
每月
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<AInput v-model:value="valueRange.start" type="number" v-bind="typeRangeAttrs" />
<span> </span>
<AInput v-model:value="valueRange.end" type="number" v-bind="typeRangeAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<AInput v-model:value="valueLoop.start" type="number" v-bind="typeLoopAttrs" />
<span> 月开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" v-bind="typeLoopAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.specify" v-bind="beforeRadioAttrs">
指定
</Radio>
<div class="list">
<CheckboxGroup v-model:value="valueList">
<template v-for="i in specifyRange" :key="i">
<Checkbox :value="i" v-bind="typeSpecifyAttrs">
{{ i }}
</Checkbox>
</template>
</CheckboxGroup>
</div>
</div>
</RadioGroup>
</div>
</template>

69
src/components/CronTab/src/tabs/SecondUI.vue

@ -1,69 +0,0 @@
<script lang="ts">
import { defineComponent } from 'vue'
import { Checkbox, Input, Radio } from 'ant-design-vue'
import { useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
export default defineComponent({
name: 'SecondUI',
components: { AInput: Input, Checkbox, CheckboxGroup: Checkbox.Group, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '*',
}),
emits: useTabEmits(),
setup(props, context) {
return useTabSetup(props, context, {
defaultValue: '*',
minValue: 0,
maxValue: 59,
valueRange: { start: 0, end: 59 },
valueLoop: { start: 0, interval: 1 },
})
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.every" v-bind="beforeRadioAttrs">
每秒
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<AInput v-model:value="valueRange.start" type="number" v-bind="typeRangeAttrs" />
<span> </span>
<AInput v-model:value="valueRange.end" type="number" v-bind="typeRangeAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<AInput v-model:value="valueLoop.start" type="number" v-bind="typeLoopAttrs" />
<span> 秒开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" v-bind="typeLoopAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.specify" v-bind="beforeRadioAttrs">
指定
</Radio>
<div class="list">
<CheckboxGroup v-model:value="valueList">
<template v-for="i in specifyRange" :key="i">
<Checkbox :value="i" v-bind="typeSpecifyAttrs">
{{ i }}
</Checkbox>
</template>
</CheckboxGroup>
</div>
</div>
</RadioGroup>
</div>
</template>

135
src/components/CronTab/src/tabs/WeekUI.vue

@ -1,135 +0,0 @@
<script lang="ts">
import { computed, defineComponent, watch } from 'vue'
import { Checkbox, Input, Radio, Select } from 'ant-design-vue'
import { TypeEnum, useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
const WEEK_MAP_EN = {
1: 'SUN',
2: 'MON',
3: 'TUE',
4: 'WED',
5: 'THU',
6: 'FRI',
7: 'SAT',
}
const WEEK_MAP_CN = {
1: '周日',
2: '周一',
3: '周二',
4: '周三',
5: '周四',
6: '周五',
7: '周六',
}
export default defineComponent({
name: 'WeekUI',
components: { AInput: Input, ASelect: Select, Checkbox, CheckboxGroup: Checkbox.Group, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '?',
props: {
day: { type: String, default: '*' },
},
}),
emits: useTabEmits(),
setup(props, context) {
const disabledChoice = computed(() => {
return (props.day && props.day !== '?') || props.disabled
})
const setup = useTabSetup(props, context, {
defaultType: TypeEnum.unset,
defaultValue: '?',
minValue: 1,
maxValue: 7,
// 0,7 1
valueRange: { start: 1, end: 7 },
valueLoop: { start: 2, interval: 1 },
disabled: disabledChoice,
})
const weekOptions = computed(() => {
const options: { label: string, value: number }[] = []
for (const weekKey of Object.keys(WEEK_MAP_CN)) {
const weekName: string = WEEK_MAP_CN[weekKey]
options.push({
value: Number.parseInt(weekKey),
label: weekName,
})
}
return options
})
const typeRangeSelectAttrs = computed(() => ({
class: ['w80'],
disabled: setup.typeRangeAttrs.value.disabled,
}))
const typeLoopSelectAttrs = computed(() => ({
class: ['w80'],
disabled: setup.typeLoopAttrs.value.disabled,
}))
watch(
() => props.day,
() => {
setup.updateValue(disabledChoice.value ? '?' : setup.computeValue.value)
},
)
return {
...setup,
weekOptions,
typeLoopSelectAttrs,
typeRangeSelectAttrs,
WEEK_MAP_CN,
WEEK_MAP_EN,
}
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.unset" v-bind="beforeRadioAttrs">
不设置
</Radio>
<span class="tip-info">日和周只能设置其中之一</span>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<ASelect v-model:value="valueRange.start" :options="weekOptions" v-bind="typeRangeSelectAttrs" />
<span> </span>
<ASelect v-model:value="valueRange.end" :options="weekOptions" v-bind="typeRangeSelectAttrs" />
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<ASelect v-model:value="valueLoop.start" :options="weekOptions" v-bind="typeLoopSelectAttrs" />
<span> 开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" v-bind="typeLoopAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.specify" v-bind="beforeRadioAttrs">
指定
</Radio>
<div class="list list-cn">
<CheckboxGroup v-model:value="valueList">
<template v-for="opt in weekOptions" :key="opt.value">
<Checkbox :value="opt.value" v-bind="typeSpecifyAttrs">
{{ opt.label }}
</Checkbox>
</template>
</CheckboxGroup>
</div>
</div>
</RadioGroup>
</div>
</template>

55
src/components/CronTab/src/tabs/YearUI.vue

@ -1,55 +0,0 @@
<script lang="ts">
import { defineComponent } from 'vue'
import { Input, Radio } from 'ant-design-vue'
import { useTabEmits, useTabProps, useTabSetup } from './useTabMixin'
export default defineComponent({
name: 'YearUI',
components: { AInput: Input, Radio, RadioGroup: Radio.Group },
props: useTabProps({
defaultValue: '*',
}),
emits: useTabEmits(),
setup(props, context) {
const nowYear = new Date().getFullYear()
return useTabSetup(props, context, {
defaultValue: '*',
minValue: 0,
valueRange: { start: nowYear, end: nowYear + 100 },
valueLoop: { start: nowYear, interval: 1 },
})
},
})
</script>
<template>
<div :class="`${prefixCls}-config-list`">
<RadioGroup v-model:value="type">
<div class="item">
<Radio :value="TypeEnum.every" v-bind="beforeRadioAttrs">
每年
</Radio>
</div>
<div class="item">
<Radio :value="TypeEnum.range" v-bind="beforeRadioAttrs">
区间
</Radio>
<span> </span>
<AInput v-model:value="valueRange.start" type="number" class="w80" v-bind="typeRangeAttrs" />
<span> </span>
<AInput v-model:value="valueRange.end" type="number" class="w80" v-bind="typeRangeAttrs" />
<span> </span>
</div>
<div class="item">
<Radio :value="TypeEnum.loop" v-bind="beforeRadioAttrs">
循环
</Radio>
<span> </span>
<AInput v-model:value="valueLoop.start" type="number" class="w80" v-bind="typeLoopAttrs" />
<span> 年开始间隔 </span>
<AInput v-model:value="valueLoop.interval" type="number" class="w80" v-bind="typeLoopAttrs" />
<span> </span>
</div>
</RadioGroup>
</div>
</template>

204
src/components/CronTab/src/tabs/useTabMixin.ts

@ -1,204 +0,0 @@
// 主要用于日和星期的互斥使用
import { computed, inject, reactive, ref, unref, watch } from 'vue'
import { propTypes } from '@/utils/propTypes'
export enum TypeEnum {
unset = 'UNSET',
every = 'EVERY',
range = 'RANGE',
loop = 'LOOP',
work = 'WORK',
last = 'LAST',
specify = 'SPECIFY',
}
// use 公共 props
export function useTabProps(options) {
const defaultValue = options?.defaultValue ?? '?'
return {
value: propTypes.string.def(defaultValue),
disabled: propTypes.bool.def(false),
...options?.props,
}
}
// use 公共 emits
export function useTabEmits() {
return ['change', 'update:value']
}
// use 公共 setup
export function useTabSetup(props, context, options) {
const { emit } = context
const prefixCls = inject('prefixCls')
const defaultValue = ref(options?.defaultValue ?? '?')
// 类型
const type = ref(options.defaultType ?? TypeEnum.every)
const valueList = ref<any[]>([])
// 对于不同的类型,所定义的值也有所不同
const valueRange = reactive(options.valueRange)
const valueLoop = reactive(options.valueLoop)
const valueWeek = reactive(options.valueWeek)
const valueWork = ref(options.valueWork)
const maxValue = ref(options.maxValue)
const minValue = ref(options.minValue)
// 根据不同的类型计算出的value
const computeValue = computed(() => {
const valueArray: any[] = []
switch (type.value) {
case TypeEnum.unset:
valueArray.push('?')
break
case TypeEnum.every:
valueArray.push('*')
break
case TypeEnum.range:
valueArray.push(`${valueRange.start}-${valueRange.end}`)
break
case TypeEnum.loop:
valueArray.push(`${valueLoop.start}/${valueLoop.interval}`)
break
case TypeEnum.work:
valueArray.push(`${valueWork.value}W`)
break
case TypeEnum.last:
valueArray.push('L')
break
case TypeEnum.specify:
if (valueList.value.length === 0)
valueList.value.push(minValue.value)
valueArray.push(valueList.value.join(','))
break
default:
valueArray.push(defaultValue.value)
break
}
return valueArray.length > 0 ? valueArray.join('') : defaultValue.value
})
// 指定值范围区间,介于最小值和最大值之间
const specifyRange = computed(() => {
const range: number[] = []
if (maxValue.value != null) {
for (let i = minValue.value; i <= maxValue.value; i++)
range.push(i)
}
return range
})
watch(
() => props.value,
(val) => {
if (val !== computeValue.value)
parseValue(val)
},
{ immediate: true },
)
watch(computeValue, v => updateValue(v))
function updateValue(value) {
emit('change', value)
emit('update:value', value)
}
/**
* parseValue
* @param value
*/
function parseValue(value) {
if (value === computeValue.value)
return
try {
if (!value || value === defaultValue.value) {
type.value = TypeEnum.every
}
else if (value.includes('?')) {
type.value = TypeEnum.unset
}
else if (value.includes('-')) {
type.value = TypeEnum.range
const values = value.split('-')
if (values.length >= 2) {
valueRange.start = Number.parseInt(values[0])
valueRange.end = Number.parseInt(values[1])
}
}
else if (value.includes('/')) {
type.value = TypeEnum.loop
const values = value.split('/')
if (values.length >= 2) {
valueLoop.start = value[0] === '*' ? 0 : Number.parseInt(values[0])
valueLoop.interval = Number.parseInt(values[1])
}
}
else if (value.includes('W')) {
type.value = TypeEnum.work
const values = value.split('W')
if (!values[0] && !Number.isNaN(values[0]))
valueWork.value = Number.parseInt(values[0])
}
else if (value.includes('L')) {
type.value = TypeEnum.last
}
else if (value.includes(',') || !Number.isNaN(value)) {
type.value = TypeEnum.specify
valueList.value = value.split(',').map(item => Number.parseInt(item))
}
else {
type.value = TypeEnum.every
}
}
catch (e) {
type.value = TypeEnum.every
}
}
const beforeRadioAttrs = computed(() => ({
class: ['choice'],
disabled: props.disabled || unref(options.disabled),
}))
const inputNumberAttrs = computed(() => ({
class: ['w60'],
max: maxValue.value,
min: minValue.value,
precision: 0,
}))
const typeRangeAttrs = computed(() => ({
disabled: type.value !== TypeEnum.range || props.disabled || unref(options.disabled),
...inputNumberAttrs.value,
}))
const typeLoopAttrs = computed(() => ({
disabled: type.value !== TypeEnum.loop || props.disabled || unref(options.disabled),
...inputNumberAttrs.value,
}))
const typeSpecifyAttrs = computed(() => ({
disabled: type.value !== TypeEnum.specify || props.disabled || unref(options.disabled),
class: ['list-check-item'],
}))
return {
type,
TypeEnum,
prefixCls,
defaultValue,
valueRange,
valueLoop,
valueWeek,
valueList,
valueWork,
maxValue,
minValue,
computeValue,
specifyRange,
updateValue,
parseValue,
beforeRadioAttrs,
inputNumberAttrs,
typeRangeAttrs,
typeLoopAttrs,
typeSpecifyAttrs,
}
}

50
src/components/CronTab/src/validator.ts

@ -1,50 +0,0 @@
/* eslint-disable prefer-promise-reject-errors */
import CronParser from 'cron-parser'
import type { ValidatorRule } from 'ant-design-vue/lib/form/interface'
const cronRule: ValidatorRule = {
// eslint-disable-next-line no-empty-pattern
validator({}, value) {
// 没填写就不校验
if (!value)
return Promise.resolve()
const values: string[] = value.split(' ').filter(item => !!item)
if (values.length > 7)
return Promise.reject('Cron表达式最多7项!')
// 检查第7项
let val: string = value
if (values.length === 7) {
const year = values[6]
if (year !== '*' && year !== '?') {
let yearValues: string[] = []
if (year.includes('-'))
yearValues = year.split('-')
else if (year.indexOf('/'))
yearValues = year.split('/')
else
yearValues = [year]
// 判断是否都是数字
const checkYear = yearValues.some(item => Number.isNaN(Number(item)))
if (checkYear)
return Promise.reject(`Cron表达式参数[年]错误:${year}`)
}
// 取其中的前六项
val = values.slice(0, 6).join(' ')
}
// 6位 没有年
// 5位没有秒、年
try {
const iter = CronParser.parseExpression(val)
iter.next()
return Promise.resolve()
}
catch (e: any) {
return Promise.reject(`Cron表达式错误:${e}`)
}
},
}
export default cronRule.validator

2
src/components/Description/src/typing.ts

@ -36,7 +36,7 @@ export interface DescriptionProps extends DescriptionsProps {
}
export interface DescInstance {
setDescProps(descProps: Partial<DescriptionProps>): void
setDescProps: (descProps: Partial<DescriptionProps>) => void
}
export type Register = (descInstance: DescInstance) => void

2
src/components/EllipsisText/src/_utils.ts

@ -1,7 +1,7 @@
// cancelAnimationFrame
export const cancelAnimationFrame = window.cancelAnimationFrame
// 使用 requestAnimationFrame 模拟 setTimeout 和 setInterval
export function rafTimeout(fn: Function, delay = 0, interval = false): object {
export function rafTimeout(fn: (...args: any) => any, delay = 0, interval = false): object {
const requestAnimationFrame
= typeof window !== 'undefined' ? window.requestAnimationFrame : () => {}
let start: any = null

2
src/components/Form/src/components/FileUpload.vue

@ -264,7 +264,7 @@ function uidGenerator() {
}
function getFileName(path) {
if (path.lastIndexOf('\\') >= 0) {
if (path.includes('\\')) {
const reg = /\\/g
path = path.replace(reg, '/')
}

10
src/components/Form/src/components/FormItem.vue

@ -312,11 +312,11 @@ export default defineComponent({
const { label, helpMessage, helpComponentProps, subLabel } = props.schema
const renderLabel = subLabel
? (
<span>
{label}
{' '}
<span class="text-secondary">{subLabel}</span>
</span>
<span>
{label}
{' '}
<span class="text-secondary">{subLabel}</span>
</span>
)
: (
label

5
src/components/Form/src/hooks/useFormEvents.ts

@ -165,7 +165,7 @@ export function useFormEvents({
validKeys.push(nestKey)
}
}
catch (e) {
catch {
// key not exist
if (isDef(defaultValueRef.value[nestKey]))
unref(formModel)[nestKey] = cloneDeep(unref(defaultValueRef.value[nestKey]))
@ -313,8 +313,9 @@ export function useFormEvents({
&& (!(item.field in currentFieldsValue)
|| isNil(currentFieldsValue[item.field])
|| isEmpty(currentFieldsValue[item.field]))
)
) {
obj[item.field] = item.defaultValue
}
})
setFieldsValue(obj)
}

4
src/components/Form/src/types/index.ts

@ -113,8 +113,6 @@ interface _CustomComponents {
ApiTransfer: ExtractPropTypes<(typeof import('../components/ApiTransfer.vue'))['default']>
InputCountDown: ExtractPropTypes<(typeof import('@/components/CountDown/src/CountdownInput.vue'))['default']>
FileUpload: ExtractPropTypes<(typeof import('../components/FileUpload.vue'))['default']>
Editor: ExtractPropTypes<(typeof import('@/components/Tinymce/src/Editor.vue'))['default']>
CronTab: ExtractPropTypes<(typeof import('@/components/CronTab/src/CronTabInput.vue'))['default']>
ApiCheckboxGroup: ExtractPropTypes<(typeof import('../components/ApiCheckboxGroup.vue'))['default']>
}
@ -160,8 +158,6 @@ interface _ComponentProps {
Divider: ExtractPropTypes<(typeof import('ant-design-vue/es/divider'))['default']>
ApiTransfer: CustomComponents['ApiTransfer'] & ExtractPropTypes<(typeof import('ant-design-vue/es/transfer'))['default']>
FileUpload: CustomComponents['FileUpload'] & ExtractPropTypes<(typeof import('ant-design-vue/es/upload'))['default']>
Editor: CustomComponents['Editor']
CronTab: CustomComponents['CronTab']
ApiCheckboxGroup: CustomComponents['ApiCheckboxGroup'] & ComponentProps['CheckboxGroup']
}

2
src/components/Markdown/src/Markdown.vue

@ -132,7 +132,7 @@ function destroy() {
try {
vditorInstance?.destroy?.()
}
catch (error) {}
catch {}
vditorRef.value = null
initedRef.value = false
}

2
src/components/Markdown/src/MarkdownViewer.vue

@ -51,7 +51,7 @@ function destroy() {
try {
vditorInstance?.destroy?.()
}
catch (error) {}
catch {}
vditorPreviewRef.value = null
}

6
src/components/Modal/src/components/ModalWrapper.vue

@ -81,9 +81,11 @@ onUnmounted(() => {
async function scrollTop() {
nextTick(() => {
const wrapperRefDom = unref(wrapperRef)
if (!wrapperRefDom)
if (!wrapperRefDom) {
return
;(wrapperRefDom as any)?.scrollTo?.(0)
}
(wrapperRefDom as any)?.scrollTo?.(0)
})
}

5
src/components/Preview/src/Functional.vue

@ -103,10 +103,11 @@ export default defineComponent({
//
function initMouseWheel() {
const wrapEl = unref(wrapElRef)
if (!wrapEl)
if (!wrapEl) {
return
}
;(wrapEl as any).onmousewheel = scrollFunc
(wrapEl as any).onmousewheel = scrollFunc
// onmousewheelDOMMouseScroll
document.body.addEventListener('DOMMouseScroll', scrollFunc)
//

19
src/components/Table/src/BasicTable.vue

@ -71,9 +71,8 @@ const getProps = computed(() => {
const isFixedHeightPage = inject(PageWrapperFixedHeightKey, false)
watchEffect(() => {
unref(isFixedHeightPage)
&& props.canResize
&& warn('\'canResize\' of BasicTable may not work in PageWrapper with \'fixedHeight\' (especially in hot updates)')
if (unref(isFixedHeightPage) && props.canResize)
warn('\'canResize\' of BasicTable may not work in PageWrapper with \'fixedHeight\' (especially in hot updates)')
})
const { getLoading, setLoading } = useLoading(getProps)
@ -130,7 +129,8 @@ function handleTableChange(pagination: any, filters: any, sorter: any, extra: an
emit('change', pagination, filters, sorter)
// useTableonChange
const { onChange } = unref(getProps)
onChange && isFunction(onChange) && onChange(pagination, filters, sorter, extra)
if (onChange && isFunction(onChange))
onChange(pagination, filters, sorter, extra)
}
const {
@ -331,13 +331,14 @@ emit('register', tableAction, formActions)
<slot name="bodyCell" v-bind="((data || {}) as SlotBodyCellProps<T>)" />
</template>
<template #expandIcon="{ expanded, record, onExpand }">
<template #expandIcon="renderExpandIconProps">
<!-- if children is an array, render ExpandIcon -->
<ExpandIcon
:class="{ invisible: !record.children }"
:expanded="expanded"
:record="record"
:on-expand="onExpand"
v-if="renderExpandIconProps"
:class="{ invisible: !renderExpandIconProps.record.children }"
:expanded="renderExpandIconProps.expanded"
:record="renderExpandIconProps.record"
:on-expand="renderExpandIconProps.onExpand"
:load-data="loadData"
/>
</template>

4
src/components/Table/src/components/HeaderCell.vue

@ -37,10 +37,10 @@ export default defineComponent({
<div>
{getIsEdit.value
? (
<EditTableHeaderCell>{getTitle.value}</EditTableHeaderCell>
<EditTableHeaderCell>{getTitle.value}</EditTableHeaderCell>
)
: (
<span class="default-header-cell">{getTitle.value}</span>
<span class="default-header-cell">{getTitle.value}</span>
)}
{getHelpMessage.value && (
<BasicHelp text={getHelpMessage.value} class={`${prefixCls}__help`} />

2
src/components/Table/src/components/editable/EditableCell.vue

@ -274,7 +274,7 @@ export default defineComponent({
value,
})
}
catch (e) {
catch {
result = false
}
finally {

3
src/components/Table/src/components/editable/helper.ts

@ -20,8 +20,9 @@ export function createPlaceholderMessage(component: ComponentType) {
|| component.includes('Switch')
|| component.includes('DatePicker')
|| component.includes('TimePicker')
)
) {
return t('common.chooseText')
}
return ''
}

2
src/components/Table/src/hooks/useColumns.ts

@ -318,7 +318,7 @@ export function formatCell(text: string, format: CellFormat, record: Recordable,
if (isMap(format))
return format.get(text)
}
catch (error) {
catch {
return text
}
}

2
src/components/Table/src/hooks/useRender.ts

@ -111,7 +111,7 @@ export const useRender = {
const data = JSON.parse(json)
return h(JsonPreview, { data })
}
catch (e) {
catch {
return json
}
}

1
src/components/Table/src/hooks/useTable.ts

@ -124,7 +124,6 @@ export function useTable<T>(tableProps?: Props<T>): [
getSize: () => {
return toRaw(getTableInstance().getSize())
},
// eslint-disable-next-line ts/ban-types
updateTableData: <K extends keyof T | (string & {})>(index: number, key: K, value: K extends keyof T ? T[K] : any) => {
return getTableInstance().updateTableData(index, key, value)
},

1
src/components/Table/src/props.ts

@ -129,7 +129,6 @@ export function defineTableProps<T>() {
default: null,
},
rowKey: {
// eslint-disable-next-line ts/ban-types
type: [String, Function] as PropType<keyof T | ((record: T) => keyof T) | (string & {})>,
default: '',
},

2
src/components/Table/src/types/column.ts

@ -138,7 +138,7 @@ export interface ColumnProps<T> {
* Sort function for local sort, see Array.sort's compareFunction. If you need sort buttons only, set to true
* @type boolean | Function
*/
sorter?: boolean | Function
sorter?: boolean | ((...args: any) => any)
/**
* Order of sorted values: 'ascend' 'descend' false

9
src/components/Table/src/types/table.ts

@ -115,7 +115,6 @@ export interface TableActionType<T = Recordable> {
getRowSelection: () => TableRowSelection<EditRecordRow<T>>
getCacheColumns: () => BasicColumn[]
emit?: EmitType
// eslint-disable-next-line ts/ban-types
updateTableData: <K extends keyof T | (string & {})>(index: number, key: K, value: K extends keyof T ? T[K] : any) => Promise<EditRecordRow<T>>
setShowPagination: (show: boolean) => Promise<void>
getShowPagination: () => boolean
@ -215,8 +214,6 @@ export interface BasicTableProps<T = Recordable<any>> {
// 在分页改变的时候清空选项
clearSelectOnPageChange?: boolean
//
// eslint-disable-next-line ts/ban-types
rowKey?: keyof T | ((record: T) => keyof T) | (string & {})
// 数据
dataSource?: T[]
@ -273,7 +270,7 @@ export interface BasicTableProps<T = Recordable<any>> {
* Customize row expand Icon.
* @type Function | VNodeChild
*/
expandIcon?: Function | VNodeChild | JSX.Element
expandIcon?: (...args: any) => any | VNodeChild | JSX.Element
/**
* Whether to expand row by clicking anywhere in the whole row
@ -291,7 +288,7 @@ export interface BasicTableProps<T = Recordable<any>> {
* Table footer renderer
* @type Function | VNodeChild
*/
footer?: Function | VNodeChild | JSX.Element
footer?: ((...args: any) => any) | VNodeChild | JSX.Element
/**
* Indent size in pixels of tree data
@ -381,7 +378,7 @@ export interface BasicTableProps<T = Recordable<any>> {
*
* @version 1.5.4
*/
transformCellText?: Function
transformCellText?: (...args: any) => any
/**
* Callback executed before editable cell submit value, not for row-editor

28
src/components/Tree/src/BasicTree.vue

@ -360,11 +360,11 @@ export default defineComponent({
const titleDom = isHighlight
? (
<span class={unref(getBindValues)?.blockNode ? `${bem('content')}` : ''}>
<span>{title.slice(0, searchIdx)}</span>
<span style={highlightStyle}>{searchText}</span>
<span>{title.slice(searchIdx + (searchText as string).length)}</span>
</span>
<span class={unref(getBindValues)?.blockNode ? `${bem('content')}` : ''}>
<span>{title.slice(0, searchIdx)}</span>
<span style={highlightStyle}>{searchText}</span>
<span>{title.slice(searchIdx + (searchText as string).length)}</span>
</span>
)
: (
title
@ -377,17 +377,17 @@ export default defineComponent({
<span class={`${bem('title')} pl-2`} onClick={handleClickNode.bind(null, item[keyField], item[childrenField])}>
{slots?.title
? (
<>
{iconDom}
{getSlot(slots, 'title', item)}
</>
<>
{iconDom}
{getSlot(slots, 'title', item)}
</>
)
: (
<>
{iconDom}
{titleDom}
<span class={bem('actions')}>{renderAction(item)}</span>
</>
<>
{iconDom}
{titleDom}
<span class={bem('actions')}>{renderAction(item)}</span>
</>
)}
</span>
)

2
src/hooks/setting/index.ts

@ -12,7 +12,7 @@ export function useGlobSetting(): Readonly<GlobConfig> {
VITE_GLOB_UPLOAD_URL,
} = getAppEnvConfig()
if (!/[a-zA-Z\_]*/.test(VITE_GLOB_APP_SHORT_NAME)) {
if (!/[a-z_]*/i.test(VITE_GLOB_APP_SHORT_NAME)) {
warn(
'VITE_GLOB_APP_SHORT_NAME Variables can only be characters/underscores, please modify in the environment variables and re-running.',
)

2
src/hooks/web/useContentHeight.ts

@ -53,7 +53,7 @@ export function useContentHeight(
function calcSubtractSpace(element: Element | null | undefined, direction: 'all' | 'top' | 'bottom' = 'all'): number {
function numberPx(px: string) {
return Number(px.replace(/[^\d]/g, ''))
return Number(px.replace(/\D/g, ''))
}
let subtractHeight = 0
const ZERO_PX = '0px'

18
src/hooks/web/useMessage.tsx

@ -8,15 +8,15 @@ import { useI18n } from './useI18n'
import { isString } from '@/utils/is'
export interface NotifyApi {
info(config: NotificationArgsProps): void
success(config: NotificationArgsProps): void
error(config: NotificationArgsProps): void
warn(config: NotificationArgsProps): void
warning(config: NotificationArgsProps): void
open(args: NotificationArgsProps): void
close(key: string): void
config(options: ConfigProps): void
destroy(): void
info: (config: NotificationArgsProps) => void
success: (config: NotificationArgsProps) => void
error: (config: NotificationArgsProps) => void
warn: (config: NotificationArgsProps) => void
warning: (config: NotificationArgsProps) => void
open: (args: NotificationArgsProps) => void
close: (key: string) => void
config: (options: ConfigProps) => void
destroy: () => void
}
export declare type NotificationPlacement = 'topLeft' | 'topRight' | 'bottomLeft' | 'bottomRight'

2
src/hooks/web/usePermission.ts

@ -27,7 +27,7 @@ export function usePermission() {
try {
router.addRoute(route as unknown as RouteRecordRaw)
}
catch (e) {}
catch {}
})
permissionStore.setLastBuildMenuTime()
closeAll()

3
src/layouts/default/header/MultipleHeader.vue

@ -64,8 +64,9 @@ const getPlaceholderDomStyle = computed((): CSSProperties => {
(unref(getShowFullHeaderRef) || !unref(getSplit))
&& unref(getShowHeader)
&& !unref(getFullContent)
)
) {
height += HEADER_HEIGHT
}
if (unref(getShowMultipleTab) && !unref(getFullContent))
height += TABS_HEIGHT

18
src/layouts/default/menu/index.vue

@ -135,17 +135,17 @@ export default defineComponent({
return null
return !props.isHorizontal
? (
<SimpleMenu {...menuProps} isSplitMenu={unref(getSplit)} items={menus} />
<SimpleMenu {...menuProps} isSplitMenu={unref(getSplit)} items={menus} />
)
: (
<BasicMenu
{...(menuProps as any)}
isHorizontal={props.isHorizontal}
type={unref(getMenuType)}
showLogo={unref(getIsShowLogo)}
mode={unref(getComputedMenuMode as any)}
items={menus}
/>
<BasicMenu
{...(menuProps as any)}
isHorizontal={props.isHorizontal}
type={unref(getMenuType)}
showLogo={unref(getIsShowLogo)}
mode={unref(getComputedMenuMode as any)}
items={menus}
/>
)
}

4
src/logics/error-handle/index.ts

@ -19,13 +19,13 @@ function processStackMsg(error: Error) {
return ''
let stack = error.stack
.replace(/\n/gi, '') // Remove line breaks to save the size of the transmitted content
.replace(/\n/g, '') // Remove line breaks to save the size of the transmitted content
.replace(/\bat\b/gi, '@') // At in chrome, @ in ff
.split('@') // Split information with @
.slice(0, 9) // The maximum stack length (Error.stackTraceLimit = 10), so only take the first 10
.map(v => v.replace(/^\s*|\s*$/g, '')) // Remove extra spaces
.join('~') // Manually add separators for later display
.replace(/\?[^:]+/gi, '') // Remove redundant parameters of js file links (?x=1 and the like)
.replace(/\?[^:]+/g, '') // Remove redundant parameters of js file links (?x=1 and the like)
const msg = error.toString()
if (!stack.includes(msg))
stack = `${msg}@${stack}`

4
src/router/guard/permissionGuard.ts

@ -87,7 +87,7 @@ export function createPermissionGuard(router: Router) {
try {
await userStore.getUserInfoAction(userInfo?.user)
}
catch (err) {
catch {
next()
return
}
@ -104,7 +104,7 @@ export function createPermissionGuard(router: Router) {
try {
router.addRoute(route as unknown as RouteRecordRaw)
}
catch (e) {}
catch {}
})
router.addRoute(PAGE_NOT_FOUND_ROUTE as unknown as RouteRecordRaw)

2
src/router/helper/menuHelper.ts

@ -81,7 +81,7 @@ export function transformRouteToMenu(routeModList: AppRouteModule[], routerMappi
/**
* config menu with given params
*/
const menuParamRegex = /(?::)([\s\S]+?)((?=\/)|$)/g
const menuParamRegex = /:([\s\S]+?)(?=\/)|$/g
export function configureDynamicParamsMenu(menu: Menu, params: RouteParams) {
const { path, paramPath } = toRaw(menu)

2
src/store/modules/lock.ts

@ -50,7 +50,7 @@ export const useLockStore = defineStore('app-lock', {
// return res
}
catch (error) {
catch {
return false
}
}

3
src/store/modules/multipleTab.ts

@ -123,8 +123,9 @@ export const useMultipleTabStore = defineStore('app-multiple-tab', {
|| path === PageEnum.BASE_LOGIN
|| !name
|| [REDIRECT_ROUTE.name, PAGE_NOT_FOUND_ROUTE.name].includes(name as string)
)
) {
return
}
let updateIndex = -1
// Existing pages, do not add tabs repeatedly

2
src/store/modules/permission.ts

@ -129,7 +129,7 @@ export const usePermissionStore = defineStore('app-permission', {
try {
patcher(routes)
}
catch (e) {
catch {
// 已处理完毕跳出循环
}
}

4
src/store/modules/user.ts

@ -129,7 +129,7 @@ export const useUserStore = defineStore('app-user', {
try {
router.addRoute(route as unknown as RouteRecordRaw)
}
catch (e) {}
catch {}
})
router.addRoute(PAGE_NOT_FOUND_ROUTE as unknown as RouteRecordRaw)
permissionStore.setDynamicAddedRoute(true)
@ -155,7 +155,7 @@ export const useUserStore = defineStore('app-user', {
.map(i => `${i[0].toUpperCase()}${i.slice(1)}`)
.join('')
const component = __menu.path.replaceAll(/\/:[\s|\S]*/g, '')
const component = __menu.path.replaceAll(/\/:[\s\S]*/g, '')
let isPadIndexExtension = false
if (!component.endsWith('index') && !/\/:/.test(__menu.path))

2
src/utils/cache/storageCache.ts vendored

@ -84,7 +84,7 @@ export function createStorage({
this.remove(key)
}
catch (e) {
catch {
return def
}
}

6
src/utils/cipher.ts

@ -10,13 +10,13 @@ import SHA512 from 'crypto-js/sha512'
// Define an interface for encryption
// 定义一个加密器的接口
export interface Encryption {
encrypt(plainText: string): string
decrypt(cipherText: string): string
encrypt: (plainText: string) => string
decrypt: (cipherText: string) => string
}
// Define an interface for Hashing
// 定义一个哈希算法的接口
export interface Hashing {
hash(data: string): string
hash: (data: string) => string
}
export interface EncryptionParams {

2
src/utils/color.ts

@ -6,7 +6,7 @@
* @return Boolean
*/
export function isHexColor(color: string) {
const reg = /^#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$/
const reg = /^#([0-9a-f]{3}|[0-9a-f]{6})$/i
return reg.test(color)
}

22
src/utils/dateUtil.ts

@ -29,28 +29,6 @@ export function betweenDay(date1, date2) {
return Math.floor((date2.getTime() - date1.getTime()) / (24 * 3600 * 1000))
}
export function formatDate(date, fmt) {
date = convertDate(date)
const o = {
'M+': date.getMonth() + 1, // 月份
'd+': date.getDate(), // 日
'H+': date.getHours(), // 小时
'm+': date.getMinutes(), // 分
's+': date.getSeconds(), // 秒
'q+': Math.floor((date.getMonth() + 3) / 3), // 季度
'S': date.getMilliseconds(), // 毫秒
}
if (/(y+)/.test(fmt)) {
// 年份
fmt = fmt.replace(RegExp.$1, (`${date.getFullYear()}`).substr(4 - RegExp.$1.length))
}
for (const k in o) {
if (new RegExp(`(${k})`).test(fmt))
fmt = fmt.replace(RegExp.$1, RegExp.$1.length === 1 ? o[k] : (`00${o[k]}`).substr((`${o[k]}`).length))
}
return fmt
}
export function addTime(date, time) {
date = convertDate(date)
return new Date(date.getTime() + time)

2
src/utils/domUtils.ts

@ -18,7 +18,7 @@ export function getBoundingClientRect(element: Element): DOMRect | number {
}
function trim(string: string) {
return (string || '').replace(/^[\s\uFEFF]+|[\s\uFEFF]+$/g, '')
return (string || '').replace(/^\s+|\s+$/g, '')
}
/* istanbul ignore next */

2
src/utils/env.ts

@ -24,7 +24,7 @@ export function getAppEnvConfig() {
VITE_GLOB_UPLOAD_URL,
} = ENV
if (!/^[a-zA-Z\_]*$/.test(VITE_GLOB_APP_SHORT_NAME)) {
if (!/^[a-z_]*$/i.test(VITE_GLOB_APP_SHORT_NAME)) {
warn(
'VITE_GLOB_APP_SHORT_NAME Variables can only be characters/underscores, please modify in the environment variables and re-running.',
)

2
src/utils/file/download.ts

@ -59,7 +59,7 @@ export function downloadByUrl({ url, target = '_blank', fileName }: { url: strin
const isChrome = window.navigator.userAgent.toLowerCase().includes('chrome')
const isSafari = window.navigator.userAgent.toLowerCase().includes('safari')
if (/(iP)/g.test(window.navigator.userAgent)) {
if (/(iP)/.test(window.navigator.userAgent)) {
console.error('Your browser does not support download!')
return false
}

3
src/utils/http/axios/Axios.ts

@ -234,8 +234,9 @@ export class VAxios {
contentType !== ContentTypeEnum.FORM_URLENCODED
|| !Reflect.has(config, 'data')
|| config.method?.toUpperCase() === RequestEnum.GET
)
) {
return config
}
return {
...config,

6
src/utils/index.ts

@ -130,7 +130,7 @@ interface EventShim {
}
export type WithInstall<T> = T & {
install(app: App): void
install: (app: App) => void
} & EventShim
export type CustomComponent = Component & { displayName?: string }
@ -176,10 +176,10 @@ export function simpleDebounce(fn, delay = 100) {
export function toCamelCase(str: string, upperCaseFirst: boolean) {
str = (str || '')
.replace(/[-|\/](.)/g, (group1) => {
.replace(/[-|/](.)/g, (group1) => {
return group1.toUpperCase()
})
.replaceAll(/[-|\/]/g, '')
.replaceAll(/[-|/]/g, '')
if (upperCaseFirst && str)
str = str.charAt(0).toUpperCase() + str.slice(1)

2
src/utils/is.ts

@ -61,6 +61,6 @@ export const isServer = typeof window === 'undefined'
export const isClient = !isServer
export function isHttpUrl(path: string): boolean {
const reg = /^http(s)?:\/\/([\w-]+\.)+[\w-]+(\/[\w- ./?%&=]*)?/
const reg = /^http(s)?:\/\/([\w\-]+\.)+[\w\-]+(\/[\w\- ./?%&=]*)?$/
return reg.test(path)
}

11
src/utils/mitt.ts

@ -25,15 +25,12 @@ export type EventHandlerMap<Events extends Record<EventType, unknown>> = Map<
export interface Emitter<Events extends Record<EventType, unknown>> {
all: EventHandlerMap<Events>
on<Key extends keyof Events>(type: Key, handler: Handler<Events[Key]>): void
on(type: '*', handler: WildcardHandler<Events>): void
on: (<Key extends keyof Events>(type: Key, handler: Handler<Events[Key]>) => void) & ((type: '*', handler: WildcardHandler<Events>) => void)
off<Key extends keyof Events>(type: Key, handler?: Handler<Events[Key]>): void
off(type: '*', handler: WildcardHandler<Events>): void
off: (<Key extends keyof Events>(type: Key, handler?: Handler<Events[Key]>) => void) & ((type: '*', handler: WildcardHandler<Events>) => void)
emit<Key extends keyof Events>(type: Key, event: Events[Key]): void
emit<Key extends keyof Events>(type: undefined extends Events[Key] ? Key : never): void
clear(): void
emit: (<Key extends keyof Events>(type: Key, event: Events[Key]) => void) & (<Key extends keyof Events>(type: undefined extends Events[Key] ? Key : never) => void)
clear: () => void
}
/**

12
src/utils/props.ts

@ -138,13 +138,13 @@ export function buildProps<
: [O[K]] extends NativePropType
? O[K]
: O[K] extends BuildPropOption<
infer T,
infer T,
infer _D,
infer R,
infer V,
infer C
>
infer _D,
infer R,
infer V,
infer C
>
? BuildPropReturn<T, O[K]['default'], R, V, C>
: never
}

2
src/utils/tree.ts

@ -268,7 +268,7 @@ export function handleTree2(data, id, parentId, children, rootId) {
// 返回每一项的子级数组
return father[id] === child[parentId]
})
// eslint-disable-next-line no-unused-expressions
branchArr.length > 0 ? (father.children = branchArr) : ''
// 返回第一层
return father[parentId] === rootId

2
vite.config.ts

@ -50,7 +50,7 @@ export default ({ command, mode }: ConfigEnv): UserConfig => {
},
// @/xxxx => src/xxxx
{
find: /\@\//,
find: /@\//,
replacement: `${pathResolve('src')}/`,
},
],

Loading…
Cancel
Save