Commit f586ddcd6a5a3015dc0d7b7f61630abc6541366b
Merge branch 'dev-fix-ww' into 'main_dev'
feat(公共接口/动态表单): 时间区间选择器新增周期范围选择配置 See merge request yunteng/thingskit-view!52
Showing
9 changed files
with
480 additions
and
23 deletions
| ... | ... | @@ -3,6 +3,7 @@ import { ExtraRequestConfigType } from "@/store/external/modules/extraComponentI |
| 3 | 3 | import { RequestConfigType } from "@/store/modules/chartEditStore/chartEditStore.d" |
| 4 | 4 | import { isShareMode } from "@/views/share/hook" |
| 5 | 5 | import { customHttp } from "./http" |
| 6 | +import { SelectTimeAggregationFieldEnum } from "@/views/chart/ContentConfigurations/components/ChartData/external/components/SelectTImeAggregation" | |
| 6 | 7 | |
| 7 | 8 | export enum ParamsType { |
| 8 | 9 | REQUIRED, |
| ... | ... | @@ -91,6 +92,21 @@ const extraValue = (object: Recordable) => { |
| 91 | 92 | }, {}) |
| 92 | 93 | } |
| 93 | 94 | |
| 95 | +const handleParams = (Params: Recordable) => { | |
| 96 | + if (Params.keys && Params?.keys?.length) { | |
| 97 | + Params.keys = (Params.keys || [] as any).join(',') | |
| 98 | + } | |
| 99 | + | |
| 100 | + const timePeriod = Params[SelectTimeAggregationFieldEnum.TIME_PERIOD] | |
| 101 | + if (timePeriod) { | |
| 102 | + Params.startTs = Date.now() - timePeriod | |
| 103 | + Params.endTs = Date.now() | |
| 104 | + Reflect.deleteProperty(Params, SelectTimeAggregationFieldEnum.TIME_PERIOD) | |
| 105 | + } | |
| 106 | + | |
| 107 | + return Object.keys(Params).filter(Boolean).reduce((prev, next) => ({ ...prev, [next]: Params[next] }), {}) | |
| 108 | +} | |
| 109 | + | |
| 94 | 110 | export const customRequest = async (request: RequestConfigType) => { |
| 95 | 111 | const { requestHttpType, requestParams, requestParamsBodyType, requestOriginUrl } = request as ExtraRequestConfigType |
| 96 | 112 | let { requestUrl } = request as ExtraRequestConfigType |
| ... | ... | @@ -105,10 +121,7 @@ export const customRequest = async (request: RequestConfigType) => { |
| 105 | 121 | |
| 106 | 122 | const body = transformBodyValue(Body, requestParamsBodyType) |
| 107 | 123 | |
| 108 | - if (Params.keys && Params?.keys?.length) { | |
| 109 | - Params.keys = (Params.keys || [] as any).join(',') | |
| 110 | - } | |
| 111 | - | |
| 124 | + Params = handleParams(Params) | |
| 112 | 125 | return customHttp.request<any>({ |
| 113 | 126 | url: requestUrl, |
| 114 | 127 | baseURL: getOriginUrl(requestOriginUrl!), | ... | ... |
src/views/chart/ContentConfigurations/components/ChartData/external/components/DynamicForm/index.vue
| ... | ... | @@ -4,6 +4,7 @@ import { FormItemInst, NDatePicker, NForm, NFormItem, NInput, NSelect, NTreeSele |
| 4 | 4 | import { computed, nextTick, ref, unref, watch } from 'vue'; |
| 5 | 5 | import { ComponentType, useDynamicPublicForm } from './useDynamicPublicForm'; |
| 6 | 6 | import { Help } from '@vicons/ionicons5' |
| 7 | +import { SelectTimeAggregation } from '../SelectTImeAggregation'; | |
| 7 | 8 | |
| 8 | 9 | const props = defineProps<{ |
| 9 | 10 | paramsItemList: ParamsItemType[] |
| ... | ... | @@ -13,7 +14,8 @@ const componentMap: { [key in ComponentType]?: any } = { |
| 13 | 14 | [ComponentType.SELECT_TREE]: NTreeSelect, |
| 14 | 15 | [ComponentType.SELECT]: NSelect, |
| 15 | 16 | [ComponentType.INPUT]: NInput, |
| 16 | - [ComponentType.DATE_PICKER]: NDatePicker | |
| 17 | + [ComponentType.DATE_PICKER]: NDatePicker, | |
| 18 | + [ComponentType.SELECT_TIME_AGGREGATION]: SelectTimeAggregation | |
| 17 | 19 | } |
| 18 | 20 | |
| 19 | 21 | const getParamsItemList = computed(() => { | ... | ... |
| 1 | +enum TimeUnitEnum { | |
| 2 | + SECOND = 'SECOND', | |
| 3 | + MINUTE = 'MINUTE', | |
| 4 | + HOUR = 'HOUR', | |
| 5 | + DAY = 'DAY', | |
| 6 | +} | |
| 7 | + | |
| 8 | +const unitMapping = { | |
| 9 | + [TimeUnitEnum.SECOND]: '秒', | |
| 10 | + [TimeUnitEnum.MINUTE]: '分', | |
| 11 | + [TimeUnitEnum.HOUR]: '小时', | |
| 12 | + [TimeUnitEnum.DAY]: '天', | |
| 13 | +} | |
| 14 | + | |
| 15 | +const unitConversion = { | |
| 16 | + [TimeUnitEnum.SECOND]: 1 * 1000, | |
| 17 | + [TimeUnitEnum.MINUTE]: 1 * 60 * 1000, | |
| 18 | + [TimeUnitEnum.HOUR]: 1 * 60 * 60 * 1000, | |
| 19 | + [TimeUnitEnum.DAY]: 1 * 60 * 60 * 24 * 1000, | |
| 20 | +} | |
| 21 | + | |
| 22 | +export const defaultIntervalOptions = [ | |
| 23 | + { | |
| 24 | + id: 1, | |
| 25 | + unit: TimeUnitEnum.SECOND, | |
| 26 | + linkage: [ | |
| 27 | + { id: 1, unit: TimeUnitEnum.SECOND } | |
| 28 | + ] | |
| 29 | + }, | |
| 30 | + { | |
| 31 | + id: 5, | |
| 32 | + unit: TimeUnitEnum.SECOND, | |
| 33 | + linkage: [ | |
| 34 | + { id: 1, unit: TimeUnitEnum.SECOND } | |
| 35 | + ] | |
| 36 | + }, | |
| 37 | + { | |
| 38 | + id: 10, | |
| 39 | + unit: TimeUnitEnum.SECOND, | |
| 40 | + linkage: [ | |
| 41 | + { id: 1, unit: TimeUnitEnum.SECOND } | |
| 42 | + ] | |
| 43 | + }, | |
| 44 | + { | |
| 45 | + id: 15, | |
| 46 | + unit: TimeUnitEnum.SECOND, | |
| 47 | + linkage: [ | |
| 48 | + { id: 1, unit: TimeUnitEnum.SECOND } | |
| 49 | + ] | |
| 50 | + }, | |
| 51 | + { | |
| 52 | + id: 30, | |
| 53 | + unit: TimeUnitEnum.SECOND, | |
| 54 | + linkage: [ | |
| 55 | + { id: 1, unit: TimeUnitEnum.SECOND } | |
| 56 | + ] | |
| 57 | + }, | |
| 58 | + { | |
| 59 | + id: 1, | |
| 60 | + unit: TimeUnitEnum.MINUTE, | |
| 61 | + linkage: [ | |
| 62 | + { id: 1, unit: TimeUnitEnum.SECOND }, | |
| 63 | + { id: 5, unit: TimeUnitEnum.SECOND }, | |
| 64 | + ] | |
| 65 | + }, | |
| 66 | + { | |
| 67 | + id: 2, | |
| 68 | + unit: TimeUnitEnum.MINUTE, | |
| 69 | + linkage: [ | |
| 70 | + { id: 1, unit: TimeUnitEnum.SECOND }, | |
| 71 | + { id: 5, unit: TimeUnitEnum.SECOND }, | |
| 72 | + { id: 10, unit: TimeUnitEnum.SECOND }, | |
| 73 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 74 | + ] | |
| 75 | + }, | |
| 76 | + { | |
| 77 | + id: 5, | |
| 78 | + unit: TimeUnitEnum.MINUTE, | |
| 79 | + linkage: [ | |
| 80 | + { id: 1, unit: TimeUnitEnum.SECOND }, | |
| 81 | + { id: 5, unit: TimeUnitEnum.SECOND }, | |
| 82 | + { id: 10, unit: TimeUnitEnum.SECOND }, | |
| 83 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 84 | + { id: 30, unit: TimeUnitEnum.SECOND }, | |
| 85 | + ] | |
| 86 | + }, | |
| 87 | + { | |
| 88 | + id: 10, | |
| 89 | + unit: TimeUnitEnum.MINUTE, | |
| 90 | + linkage: [ | |
| 91 | + { id: 5, unit: TimeUnitEnum.SECOND }, | |
| 92 | + { id: 10, unit: TimeUnitEnum.SECOND }, | |
| 93 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 94 | + { id: 30, unit: TimeUnitEnum.SECOND }, | |
| 95 | + { id: 1, unit: TimeUnitEnum.MINUTE }, | |
| 96 | + ] | |
| 97 | + }, | |
| 98 | + { | |
| 99 | + id: 15, | |
| 100 | + unit: TimeUnitEnum.MINUTE, | |
| 101 | + linkage: [ | |
| 102 | + { id: 5, unit: TimeUnitEnum.SECOND }, | |
| 103 | + { id: 10, unit: TimeUnitEnum.SECOND }, | |
| 104 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 105 | + { id: 30, unit: TimeUnitEnum.SECOND }, | |
| 106 | + { id: 1, unit: TimeUnitEnum.MINUTE }, | |
| 107 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 108 | + ] | |
| 109 | + }, | |
| 110 | + { | |
| 111 | + id: 30, | |
| 112 | + unit: TimeUnitEnum.MINUTE, | |
| 113 | + linkage: [ | |
| 114 | + { id: 5, unit: TimeUnitEnum.SECOND }, | |
| 115 | + { id: 10, unit: TimeUnitEnum.SECOND }, | |
| 116 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 117 | + { id: 30, unit: TimeUnitEnum.SECOND }, | |
| 118 | + { id: 1, unit: TimeUnitEnum.MINUTE }, | |
| 119 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 120 | + ] | |
| 121 | + }, | |
| 122 | + { | |
| 123 | + id: 1, | |
| 124 | + unit: TimeUnitEnum.HOUR, | |
| 125 | + linkage: [ | |
| 126 | + { id: 10, unit: TimeUnitEnum.SECOND }, | |
| 127 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 128 | + { id: 30, unit: TimeUnitEnum.SECOND }, | |
| 129 | + { id: 1, unit: TimeUnitEnum.MINUTE }, | |
| 130 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 131 | + { id: 5, unit: TimeUnitEnum.MINUTE }, | |
| 132 | + ] | |
| 133 | + }, | |
| 134 | + { | |
| 135 | + id: 2, | |
| 136 | + unit: TimeUnitEnum.HOUR, | |
| 137 | + linkage: [ | |
| 138 | + { id: 15, unit: TimeUnitEnum.SECOND }, | |
| 139 | + { id: 30, unit: TimeUnitEnum.SECOND }, | |
| 140 | + { id: 1, unit: TimeUnitEnum.MINUTE }, | |
| 141 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 142 | + { id: 5, unit: TimeUnitEnum.MINUTE }, | |
| 143 | + { id: 10, unit: TimeUnitEnum.MINUTE }, | |
| 144 | + { id: 15, unit: TimeUnitEnum.MINUTE }, | |
| 145 | + ] | |
| 146 | + }, | |
| 147 | + { | |
| 148 | + id: 5, | |
| 149 | + unit: TimeUnitEnum.HOUR, | |
| 150 | + linkage: [ | |
| 151 | + { id: 1, unit: TimeUnitEnum.MINUTE }, | |
| 152 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 153 | + { id: 5, unit: TimeUnitEnum.MINUTE }, | |
| 154 | + { id: 10, unit: TimeUnitEnum.MINUTE }, | |
| 155 | + { id: 15, unit: TimeUnitEnum.MINUTE }, | |
| 156 | + { id: 30, unit: TimeUnitEnum.MINUTE }, | |
| 157 | + ] | |
| 158 | + }, | |
| 159 | + { | |
| 160 | + id: 10, | |
| 161 | + unit: TimeUnitEnum.HOUR, | |
| 162 | + linkage: [ | |
| 163 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 164 | + { id: 5, unit: TimeUnitEnum.MINUTE }, | |
| 165 | + { id: 10, unit: TimeUnitEnum.MINUTE }, | |
| 166 | + { id: 15, unit: TimeUnitEnum.MINUTE }, | |
| 167 | + { id: 30, unit: TimeUnitEnum.MINUTE }, | |
| 168 | + { id: 1, unit: TimeUnitEnum.HOUR }, | |
| 169 | + ] | |
| 170 | + }, | |
| 171 | + { | |
| 172 | + id: 12, | |
| 173 | + unit: TimeUnitEnum.HOUR, | |
| 174 | + linkage: [ | |
| 175 | + { id: 2, unit: TimeUnitEnum.MINUTE }, | |
| 176 | + { id: 5, unit: TimeUnitEnum.MINUTE }, | |
| 177 | + { id: 10, unit: TimeUnitEnum.MINUTE }, | |
| 178 | + { id: 15, unit: TimeUnitEnum.MINUTE }, | |
| 179 | + { id: 30, unit: TimeUnitEnum.MINUTE }, | |
| 180 | + { id: 1, unit: TimeUnitEnum.HOUR }, | |
| 181 | + ] | |
| 182 | + }, | |
| 183 | + { | |
| 184 | + id: 1, | |
| 185 | + unit: TimeUnitEnum.DAY, | |
| 186 | + linkage: [ | |
| 187 | + { id: 5, unit: TimeUnitEnum.MINUTE }, | |
| 188 | + { id: 10, unit: TimeUnitEnum.MINUTE }, | |
| 189 | + { id: 15, unit: TimeUnitEnum.MINUTE }, | |
| 190 | + { id: 30, unit: TimeUnitEnum.MINUTE }, | |
| 191 | + { id: 1, unit: TimeUnitEnum.HOUR }, | |
| 192 | + { id: 2, unit: TimeUnitEnum.HOUR }, | |
| 193 | + ] | |
| 194 | + }, | |
| 195 | + { | |
| 196 | + id: 7, | |
| 197 | + unit: TimeUnitEnum.DAY, | |
| 198 | + linkage: [ | |
| 199 | + { id: 30, unit: TimeUnitEnum.MINUTE }, | |
| 200 | + { id: 1, unit: TimeUnitEnum.HOUR }, | |
| 201 | + { id: 2, unit: TimeUnitEnum.HOUR }, | |
| 202 | + { id: 5, unit: TimeUnitEnum.HOUR }, | |
| 203 | + { id: 10, unit: TimeUnitEnum.HOUR }, | |
| 204 | + { id: 12, unit: TimeUnitEnum.HOUR }, | |
| 205 | + { id: 1, unit: TimeUnitEnum.DAY }, | |
| 206 | + ] | |
| 207 | + }, | |
| 208 | + { | |
| 209 | + id: 30, | |
| 210 | + unit: TimeUnitEnum.DAY, | |
| 211 | + linkage: [ | |
| 212 | + { id: 2, unit: TimeUnitEnum.HOUR }, | |
| 213 | + { id: 5, unit: TimeUnitEnum.HOUR }, | |
| 214 | + { id: 10, unit: TimeUnitEnum.HOUR }, | |
| 215 | + { id: 12, unit: TimeUnitEnum.HOUR }, | |
| 216 | + { id: 1, unit: TimeUnitEnum.DAY }, | |
| 217 | + ] | |
| 218 | + }, | |
| 219 | +].map(item => { | |
| 220 | + return { | |
| 221 | + id: item.id * unitConversion[item.unit], | |
| 222 | + name: item.id + unitMapping[item.unit], | |
| 223 | + linkage: item.linkage.map(item => { | |
| 224 | + return { | |
| 225 | + id: item.id * unitConversion[item.unit], | |
| 226 | + name: item.id + unitMapping[item.unit], | |
| 227 | + } | |
| 228 | + }) | |
| 229 | + } | |
| 230 | +}) | |
| 231 | + | |
| 232 | +export const aggergationOptions = [ | |
| 233 | + { id: 'AVG', name: '平均值' }, | |
| 234 | + { id: 'MIN', name: '最小值' }, | |
| 235 | + { id: 'MAX', name: '最大值' }, | |
| 236 | + { id: 'SUM', name: '求和' }, | |
| 237 | + { id: 'COUNT', name: '计数' }, | |
| 238 | + { id: 'NONE', name: '空' }, | |
| 239 | +] | ... | ... |
| ... | ... | @@ -6,6 +6,8 @@ import { RequestConfigType } from "@/store/modules/chartEditStore/chartEditStore |
| 6 | 6 | import { DatePickerProps, FormItemRule, InputProps, SelectProps, TreeSelectProps } from "naive-ui" |
| 7 | 7 | import { computed, onMounted, reactive, Ref, ref, unref } from "vue" |
| 8 | 8 | import { DictEnum } from '@/enums/external/dictEnum' |
| 9 | +import { SelectTimeAggregationFieldEnum, SelectTimeAggregationValueTypw } from "../SelectTImeAggregation" | |
| 10 | +import { isArray } from "@/utils" | |
| 9 | 11 | |
| 10 | 12 | const GROUP_SEPARATOR = ',' |
| 11 | 13 | |
| ... | ... | @@ -15,7 +17,8 @@ export enum BuiltInVariable { |
| 15 | 17 | ORGANIZATION_ID = 'organizationId', |
| 16 | 18 | DEVICE_PROFILE_ID = 'deviceProfileId', |
| 17 | 19 | DATE_FIXED = 'fixed_date', |
| 18 | - DATE_RANGE = 'date_range' | |
| 20 | + DATE_RANGE = 'date_range', | |
| 21 | + SELECT_TIME_AGGREGATION = 'selectTimeAggregation' | |
| 19 | 22 | } |
| 20 | 23 | |
| 21 | 24 | export enum ComponentType { |
| ... | ... | @@ -23,6 +26,7 @@ export enum ComponentType { |
| 23 | 26 | SELECT_TREE = 'selectTree', |
| 24 | 27 | DATE_PICKER = 'datePicker', |
| 25 | 28 | INPUT = 'input', |
| 29 | + SELECT_TIME_AGGREGATION = 'selectTimeAggregation' | |
| 26 | 30 | } |
| 27 | 31 | |
| 28 | 32 | |
| ... | ... | @@ -57,7 +61,9 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 57 | 61 | |
| 58 | 62 | const builtInVariable = ref<BuiltInVariableRecord>() |
| 59 | 63 | |
| 60 | - const params = reactive<Recordable & { [key in BuiltInVariable]?: any }>({}) | |
| 64 | + const params = reactive<Recordable & { [key in BuiltInVariable]?: any }>({ | |
| 65 | + [BuiltInVariable.SELECT_TIME_AGGREGATION]: {} | |
| 66 | + }) | |
| 61 | 67 | |
| 62 | 68 | const optionsSet = reactive<Recordable>({}) |
| 63 | 69 | |
| ... | ... | @@ -109,7 +115,6 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 109 | 115 | if (!validIsExist(BuiltInVariable.DEVICE_PROFILE_ID) || !validIsExist(BuiltInVariable.ORGANIZATION_ID) || !params[BuiltInVariable.ORGANIZATION_ID]) return |
| 110 | 116 | const result: Recordable[] = await getDeviceList({ [BuiltInVariable.ORGANIZATION_ID]: params[BuiltInVariable.ORGANIZATION_ID], [BuiltInVariable.DEVICE_PROFILE_ID]: params[BuiltInVariable.DEVICE_PROFILE_ID] }) |
| 111 | 117 | optionsSet[BuiltInVariable.ENTITY_ID] = result.map(item => ({ ...item, alias: item.alias || item.name })) |
| 112 | - console.log(optionsSet[BuiltInVariable.ENTITY_ID]) | |
| 113 | 118 | } |
| 114 | 119 | |
| 115 | 120 | const getDeviceAttrOption = async () => { |
| ... | ... | @@ -121,6 +126,7 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 121 | 126 | |
| 122 | 127 | const getValue = computed(() => { |
| 123 | 128 | const value = { ...unref(params) } |
| 129 | + | |
| 124 | 130 | if (Reflect.has(value, BuiltInVariable.DATE_FIXED)) { |
| 125 | 131 | const fieldMapping = unref(getParams).find(item => item.key === BuiltInVariable.DATE_FIXED) |
| 126 | 132 | Reflect.set(value, fieldMapping?.value || '', value[BuiltInVariable.DATE_FIXED]) |
| ... | ... | @@ -130,13 +136,24 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 130 | 136 | if (Reflect.has(value, BuiltInVariable.DATE_RANGE)) { |
| 131 | 137 | const fieldMapping = unref(getParams).find(item => item.key === BuiltInVariable.DATE_RANGE) |
| 132 | 138 | const [start, end] = ((fieldMapping || {}).value || '').split(GROUP_SEPARATOR) |
| 133 | - const [startValue, endValue] = value[BuiltInVariable.DATE_RANGE] || [] | |
| 139 | + const dateRangeValue = value[BuiltInVariable.DATE_RANGE] | |
| 140 | + const [startValue, endValue] = isArray(dateRangeValue) ? dateRangeValue : [null, null] | |
| 134 | 141 | value[start] = startValue |
| 135 | 142 | value[end] = endValue |
| 136 | - | |
| 137 | 143 | Reflect.deleteProperty(value, BuiltInVariable.DATE_RANGE) |
| 138 | 144 | } |
| 139 | 145 | |
| 146 | + if (Reflect.has(value, BuiltInVariable.SELECT_TIME_AGGREGATION)) { | |
| 147 | + const fieldMapping = unref(getParams).find(item => item.key === BuiltInVariable.DATE_RANGE) | |
| 148 | + const [start, end] = ((fieldMapping || {}).value || '').split(GROUP_SEPARATOR) | |
| 149 | + const aggregation = Reflect.get(value, BuiltInVariable.SELECT_TIME_AGGREGATION) || {} | |
| 150 | + const result = { ...aggregation, [start]: aggregation.startTs, [end]: aggregation.endTs } | |
| 151 | + Reflect.deleteProperty(result, SelectTimeAggregationFieldEnum.START_TS) | |
| 152 | + Reflect.deleteProperty(result, SelectTimeAggregationFieldEnum.END_TS) | |
| 153 | + Object.assign(value, { ...result, [start]: aggregation.startTs, [end]: aggregation.endTs }) | |
| 154 | + Reflect.deleteProperty(value, BuiltInVariable.SELECT_TIME_AGGREGATION) | |
| 155 | + } | |
| 156 | + | |
| 140 | 157 | return value |
| 141 | 158 | }) |
| 142 | 159 | |
| ... | ... | @@ -240,6 +257,15 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 240 | 257 | } as InputProps |
| 241 | 258 | } |
| 242 | 259 | |
| 260 | + const getSelectTimeAggregation = computed(() => { | |
| 261 | + return { | |
| 262 | + value: params[BuiltInVariable.SELECT_TIME_AGGREGATION], | |
| 263 | + onChange(value: SelectTimeAggregationValueTypw) { | |
| 264 | + params[BuiltInVariable.SELECT_TIME_AGGREGATION] = value | |
| 265 | + } | |
| 266 | + } | |
| 267 | + }) | |
| 268 | + | |
| 243 | 269 | const builtInVariableConfiguration: { [key in BuiltInVariable]?: DynamicFormSchema } = { |
| 244 | 270 | [BuiltInVariable.ORGANIZATION_ID]: { |
| 245 | 271 | component: ComponentType.SELECT_TREE, |
| ... | ... | @@ -270,9 +296,31 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 270 | 296 | component: ComponentType.DATE_PICKER, |
| 271 | 297 | key: BuiltInVariable.DATE_FIXED, |
| 272 | 298 | props: getSelectDate |
| 299 | + }, | |
| 300 | + } | |
| 301 | + | |
| 302 | + const moresComponentConfiguration: { [key in BuiltInVariable]?: DynamicFormSchema } = { | |
| 303 | + [BuiltInVariable.DATE_RANGE]: { | |
| 304 | + component: ComponentType.SELECT_TIME_AGGREGATION, | |
| 305 | + key: BuiltInVariable.SELECT_TIME_AGGREGATION, | |
| 306 | + props: getSelectTimeAggregation | |
| 273 | 307 | } |
| 274 | 308 | } |
| 275 | 309 | |
| 310 | + const timePeriodRules = (required: boolean, key: string, message: string) => { | |
| 311 | + return [{ | |
| 312 | + trigger: ['blur', 'change'], | |
| 313 | + validator() { | |
| 314 | + const record = params[BuiltInVariable.SELECT_TIME_AGGREGATION] | |
| 315 | + if (required && ![record[SelectTimeAggregationFieldEnum.AGG], record[SelectTimeAggregationFieldEnum.INTERVAL], record[SelectTimeAggregationFieldEnum.END_TS], record[SelectTimeAggregationFieldEnum.START_TS]].every(Boolean)) { | |
| 316 | + validFlag.value = false | |
| 317 | + return new Error(`${message}需要填写完整`) | |
| 318 | + } | |
| 319 | + validFlag.value = true | |
| 320 | + } | |
| 321 | + }] as FormItemRule | |
| 322 | + } | |
| 323 | + | |
| 276 | 324 | const validFlag = ref(true) |
| 277 | 325 | |
| 278 | 326 | const createRules = (required: boolean, key: string, message: string) => { |
| ... | ... | @@ -288,20 +336,25 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 288 | 336 | }] as FormItemRule |
| 289 | 337 | } |
| 290 | 338 | |
| 291 | - const toFormSchemas = (builtInVariableKey: string, required: boolean, value: any) => { | |
| 339 | + const toFormSchemas = (builtInVariableKey: string, required: boolean, value: any, mores: boolean) => { | |
| 292 | 340 | const groupList = (builtInVariableKey || '').split(GROUP_SEPARATOR) |
| 293 | 341 | return groupList.reduce((prev, next) => { |
| 294 | - const result = builtInVariableConfiguration[next as BuiltInVariable] | |
| 295 | - const props = unref(result?.props) | |
| 342 | + let result = builtInVariableConfiguration[next as BuiltInVariable] | |
| 343 | + let props = unref(result?.props) | |
| 296 | 344 | const name = (unref(builtInVariable) || {})[next as BuiltInVariable]?.itemText |
| 297 | 345 | let schema: DynamicFormSchema |
| 298 | - if (builtInVariableConfiguration[next as BuiltInVariable]) { | |
| 346 | + if (result) { | |
| 347 | + if (mores) { | |
| 348 | + result = moresComponentConfiguration[next as BuiltInVariable] | |
| 349 | + props = unref(result?.props) | |
| 350 | + } | |
| 351 | + | |
| 299 | 352 | schema = { |
| 300 | 353 | ...result, |
| 301 | 354 | props, |
| 302 | 355 | name, |
| 303 | 356 | required, |
| 304 | - rules: createRules(required, next, name || next) | |
| 357 | + rules: mores ? timePeriodRules(required, next, name || next) : createRules(required, next, name || next) | |
| 305 | 358 | } as DynamicFormSchema |
| 306 | 359 | } else { |
| 307 | 360 | schema = { |
| ... | ... | @@ -313,7 +366,6 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 313 | 366 | rules: createRules(required, value, value) |
| 314 | 367 | } as DynamicFormSchema |
| 315 | 368 | } |
| 316 | - | |
| 317 | 369 | return [...prev, schema] |
| 318 | 370 | |
| 319 | 371 | }, [] as DynamicFormSchema[]) |
| ... | ... | @@ -321,10 +373,11 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 321 | 373 | } |
| 322 | 374 | |
| 323 | 375 | const getDynamicFormSchemas = computed<DynamicFormSchema[]>(() => { |
| 324 | - return unref(getParams).reduce((prev: DynamicFormSchema[], { key, value, required }) => { | |
| 325 | - const schemas = toFormSchemas(key, required, value) | |
| 376 | + const result = unref(getParams).reduce((prev: DynamicFormSchema[], { key, value, required, mores }) => { | |
| 377 | + const schemas = toFormSchemas(key, required, value, mores) | |
| 326 | 378 | return [...prev, ...schemas] |
| 327 | 379 | }, [] as DynamicFormSchema[]) |
| 380 | + return result | |
| 328 | 381 | }) |
| 329 | 382 | |
| 330 | 383 | const createForm = async () => { |
| ... | ... | @@ -335,15 +388,22 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 335 | 388 | } |
| 336 | 389 | |
| 337 | 390 | const setParams = (Params: Recordable = {}) => { |
| 338 | - for (const { key, value } of unref(getParams)) { | |
| 391 | + for (const { key, value, mores } of unref(getParams)) { | |
| 339 | 392 | const splitKeys = value ? value.split(GROUP_SEPARATOR) : key.split(GROUP_SEPARATOR) |
| 340 | 393 | if (isDateComponent(key as BuiltInVariable)) { |
| 341 | 394 | if (key as BuiltInVariable === BuiltInVariable.DATE_FIXED) { |
| 342 | 395 | params[key] = Params[splitKeys[0]] || null |
| 343 | 396 | continue |
| 344 | 397 | } |
| 345 | - const value = [Params[splitKeys[0]], Params[splitKeys[1]]] | |
| 346 | - params[key] = value.every(Boolean) ? value : null | |
| 398 | + if (mores) { | |
| 399 | + const { agg, interval, limit } = Params | |
| 400 | + const startTs = Params[splitKeys[0]] | |
| 401 | + const endTs = Params[splitKeys[1]] | |
| 402 | + params[BuiltInVariable.SELECT_TIME_AGGREGATION] = { agg, interval, startTs, endTs, limit } | |
| 403 | + } else { | |
| 404 | + const value = [Params[splitKeys[0]], Params[splitKeys[1]]] | |
| 405 | + params[key] = value.every(Boolean) ? value : null | |
| 406 | + } | |
| 347 | 407 | continue |
| 348 | 408 | } |
| 349 | 409 | for (const temp of splitKeys) { |
| ... | ... | @@ -356,6 +416,7 @@ export const useDynamicPublicForm = (paramsItemList: Ref<ParamsItemType[]>) => { |
| 356 | 416 | Object.keys(params).forEach(key => { |
| 357 | 417 | Reflect.deleteProperty(params, key) |
| 358 | 418 | }) |
| 419 | + params[BuiltInVariable.SELECT_TIME_AGGREGATION] = {} | |
| 359 | 420 | } |
| 360 | 421 | |
| 361 | 422 | const setDynamicFormValue = (params: Recordable) => { | ... | ... |
| 1 | +export { default as SelectTimeAggregation } from './index.vue' | |
| 2 | + | |
| 3 | +export interface SelectTimeAggregationValueTypw { | |
| 4 | + timePeriod?: Nullable<number> | |
| 5 | + startTs?: Nullable<number> | |
| 6 | + endTs?: Nullable<number> | |
| 7 | + agg?: Nullable<string> | |
| 8 | + interval?: Nullable<number> | |
| 9 | +} | |
| 10 | + | |
| 11 | + | |
| 12 | +export enum SelectTimeAggregationFieldEnum { | |
| 13 | + TIME_PERIOD = 'timePeriod', | |
| 14 | + START_TS = 'startTs', | |
| 15 | + END_TS = 'endTs', | |
| 16 | + AGG = 'agg', | |
| 17 | + INTERVAL = 'interval' | |
| 18 | +} | |
| 19 | + | ... | ... |
| 1 | +<script lang="ts" setup> | |
| 2 | +import { NFormItem, NGi, NGrid, NSelect, NDatePicker, NInputNumber } from 'naive-ui'; | |
| 3 | +import { defaultIntervalOptions, aggergationOptions } from '../DynamicForm/timeInterval' | |
| 4 | +import { unref, computed, ref, watch } from 'vue'; | |
| 5 | +import { isObject } from '@/utils/external/is'; | |
| 6 | + | |
| 7 | +interface Value { | |
| 8 | + agg?: Nullable<string> | |
| 9 | + interval?: Nullable<number> | |
| 10 | + startTs?: Nullable<number> | |
| 11 | + endTs?: Nullable<number> | |
| 12 | + limit?: Nullable<number> | |
| 13 | +} | |
| 14 | + | |
| 15 | +const props = withDefaults( | |
| 16 | + defineProps<{ | |
| 17 | + value?: Value | |
| 18 | + }>(), | |
| 19 | + { | |
| 20 | + value: () => ({}) | |
| 21 | + } | |
| 22 | +) | |
| 23 | + | |
| 24 | +const emit = defineEmits<{ | |
| 25 | + (e: 'update:value', value: Value): void | |
| 26 | + (e: 'change', value: Value): void | |
| 27 | +}>() | |
| 28 | + | |
| 29 | + | |
| 30 | +const timePeriod = ref<Nullable<[number, number]>>(null) | |
| 31 | +const agg = ref() | |
| 32 | +const interval = ref() | |
| 33 | +const limit = ref(7) | |
| 34 | + | |
| 35 | +const getRangeOptions = (number: number) => { | |
| 36 | + for (let i = 0; i < defaultIntervalOptions.length; i++) { | |
| 37 | + const option = defaultIntervalOptions[i] | |
| 38 | + if (option.id >= number || i === defaultIntervalOptions.length - 1) { | |
| 39 | + return option.linkage | |
| 40 | + } | |
| 41 | + | |
| 42 | + } | |
| 43 | +} | |
| 44 | + | |
| 45 | +const getShowLimit = computed(() => { | |
| 46 | + return unref(agg) === 'NONE' | |
| 47 | +}) | |
| 48 | + | |
| 49 | +const getIntervalTimeOptions = computed(() => { | |
| 50 | + const [startTs, endTs] = unref(timePeriod) || [] | |
| 51 | + if (!startTs || !endTs) return [] | |
| 52 | + const diff = Math.abs(startTs - endTs) | |
| 53 | + return getRangeOptions(diff) | |
| 54 | +}) | |
| 55 | + | |
| 56 | +const handleTimePerionChange = (value: number[]) => { | |
| 57 | + const [startTs, endTs] = value | |
| 58 | + emit('update:value', { ...props.value, startTs, endTs, interval: null }) | |
| 59 | + emit('change', { ...props.value || {}, startTs, endTs, interval: null }) | |
| 60 | +} | |
| 61 | + | |
| 62 | +const handleAggChange = (value: string) => { | |
| 63 | + const _value = { ...props.value, agg: value, ...(value === 'NONE' ? { limit: 7 } : {}) } | |
| 64 | + Reflect.deleteProperty(_value, value === 'NONE' ? 'interval' : 'limit') | |
| 65 | + emit('update:value', _value) | |
| 66 | + emit('change', _value) | |
| 67 | +} | |
| 68 | + | |
| 69 | +const handleIntervalChange = (value: number) => { | |
| 70 | + const _value = { ...props.value, interval: value } | |
| 71 | + emit('update:value', _value) | |
| 72 | + emit('change', _value) | |
| 73 | +} | |
| 74 | + | |
| 75 | +const handleLimitChange = (value: Nullable<number>) => { | |
| 76 | + const _value = { ...props.value, limit: value } | |
| 77 | + emit('update:value', _value) | |
| 78 | + emit('change', _value) | |
| 79 | +} | |
| 80 | + | |
| 81 | +watch(() => props.value, (target) => { | |
| 82 | + if (target && isObject(target)) { | |
| 83 | + const { agg: _agg, interval: _interval, startTs, endTs, limit: _limit } = target || {} | |
| 84 | + if (startTs && endTs) { | |
| 85 | + timePeriod.value = [startTs!, endTs!] | |
| 86 | + } else { | |
| 87 | + timePeriod.value = null | |
| 88 | + } | |
| 89 | + agg.value = _agg | |
| 90 | + limit.value = _limit! | |
| 91 | + interval.value = _interval | |
| 92 | + } | |
| 93 | +}) | |
| 94 | +</script> | |
| 95 | + | |
| 96 | +<template> | |
| 97 | + <NGrid :cols="24"> | |
| 98 | + <NGi :span="16"> | |
| 99 | + <NFormItem :show-label="false"> | |
| 100 | + <NDatePicker v-model:value="timePeriod" type="datetimerange" placeholder="请选择时间范围" | |
| 101 | + @update-value="handleTimePerionChange" clearable></NDatePicker> | |
| 102 | + </NFormItem> | |
| 103 | + </NGi> | |
| 104 | + <NGi :span="4"> | |
| 105 | + <NFormItem :show-label="false"> | |
| 106 | + <NSelect v-model:value="agg" @update:value="handleAggChange" :options="aggergationOptions" label-field="name" | |
| 107 | + value-field="id" placeholder="聚合方式" clearable></NSelect> | |
| 108 | + </NFormItem> | |
| 109 | + </NGi> | |
| 110 | + <NGi v-if="!getShowLimit" :span="4"> | |
| 111 | + <NFormItem :show-label="false"> | |
| 112 | + <NSelect v-model:value="interval" @update:value="handleIntervalChange" :options="getIntervalTimeOptions" | |
| 113 | + label-field="name" value-field="id" placeholder="间隔时间" clearable></NSelect> | |
| 114 | + </NFormItem> | |
| 115 | + </NGi> | |
| 116 | + <NGi v-if="getShowLimit" :span="4"> | |
| 117 | + <NFormItem :show-label="false"> | |
| 118 | + <NInputNumber v-model:value="limit" :default-value="7" @update:value="handleLimitChange" | |
| 119 | + :parse="(input: string) => parseInt(input)" :min="7" :max="50000" :step="1" placeholder="请输入最大条数" /> | |
| 120 | + </NFormItem> | |
| 121 | + </NGi> | |
| 122 | + </NGrid> | |
| 123 | +</template> | ... | ... |
| ... | ... | @@ -95,7 +95,7 @@ const getSharePageContentData = async () => { |
| 95 | 95 | } |
| 96 | 96 | setTitle(dataViewName || '') |
| 97 | 97 | showModal.value = false |
| 98 | - allowLoadPreviewPage.value = false | |
| 98 | + allowLoadPreviewPage.value = unref(isEmpty) | |
| 99 | 99 | } catch (error) { |
| 100 | 100 | console.log(error) |
| 101 | 101 | } finally { | ... | ... |