feat(sj_1.0.0): 完成通知配置

This commit is contained in:
opensnail 2024-04-28 18:19:48 +08:00
parent 33e8ec8ae6
commit 283153b0ac
9 changed files with 139 additions and 32 deletions

View File

@ -666,6 +666,9 @@ const local: App.I18n.Schema = {
notifyThreshold: 'Notify threshold', notifyThreshold: 'Notify threshold',
description: 'Describe', description: 'Describe',
notifyAttribute: 'Notify Attribute', notifyAttribute: 'Notify Attribute',
retryScene: 'Retry Scene',
job: 'Job',
workflow: 'Workflow',
form: { form: {
businessId: 'Please select Business ID', businessId: 'Please select Business ID',
description: 'Please enter Describe', description: 'Please enter Describe',

View File

@ -662,6 +662,9 @@ const local: App.I18n.Schema = {
notifyThreshold: '通知阈值', notifyThreshold: '通知阈值',
description: '描述', description: '描述',
notifyAttribute: '通知属性', notifyAttribute: '通知属性',
retryScene: '重试场景',
job: '定时任务',
workflow: '工作流',
form: { form: {
businessId: '请选择业务ID', businessId: '请选择业务ID',
description: '请输入描述', description: '请输入描述',

View File

@ -9,6 +9,15 @@ export function fetchGetJobPage(params?: Api.Job.JobSearchParams) {
}); });
} }
/** get Job list */
export function fetchGetJobList(params?: Api.Job.JobSearchParams) {
return request<Api.Job.Job[]>({
url: '/job/list',
method: 'get',
params
});
}
/** add Job */ /** add Job */
export function fetchAddJob(data: Api.Job.Job) { export function fetchAddJob(data: Api.Job.Job) {
return request<boolean>({ return request<boolean>({

View File

@ -27,6 +27,14 @@ export function fetchEditNotify(data: Api.NotifyConfig.NotifyConfig) {
}); });
} }
/** edit notify status */
export function fetchUpdateNotifyStatus(id: string, status: Api.Common.EnableStatusNumber) {
return request<boolean>({
url: `/notify-config/${id}/status/${status}`,
method: 'put'
});
}
/** get notify recipient list */ /** get notify recipient list */
export function fetchGetNotifyRecipientPageList(params?: Api.NotifyRecipient.NotifyRecipientParams) { export function fetchGetNotifyRecipientPageList(params?: Api.NotifyRecipient.NotifyRecipientParams) {
return request<Api.NotifyRecipient.NotifyRecipientList>({ return request<Api.NotifyRecipient.NotifyRecipientList>({

View File

@ -565,7 +565,7 @@ declare namespace Api {
/** 状态 */ /** 状态 */
notifyStatus: Api.Common.EnableStatusNumber; notifyStatus: Api.Common.EnableStatusNumber;
/** 通知场景 */ /** 通知场景 */
notifyScene: string; notifyScene: number;
/** 通知阈值 */ /** 通知阈值 */
notifyThreshold: number; notifyThreshold: number;
/** 限流开关 */ /** 限流开关 */

View File

@ -814,6 +814,9 @@ declare namespace App {
notifyThreshold: string; notifyThreshold: string;
description: string; description: string;
notifyAttribute: string; notifyAttribute: string;
retryScene: string;
job: string;
workflow: string;
form: { form: {
businessId: string; businessId: string;
description: string; description: string;

View File

@ -1,11 +1,13 @@
<script setup lang="tsx"> <script setup lang="tsx">
import { NButton, NPopconfirm } from 'naive-ui'; import { NButton, NPopconfirm, NTag } from 'naive-ui';
import { fetchGetNotifyConfigList } from '@/service/api'; import { fetchGetNotifyConfigList, fetchUpdateNotifyStatus } from '@/service/api';
import { $t } from '@/locales'; import { $t } from '@/locales';
import { useAppStore } from '@/store/modules/app'; import { useAppStore } from '@/store/modules/app';
import { useTable, useTableOperate } from '@/hooks/common/table'; import { useTable, useTableOperate } from '@/hooks/common/table';
import NotifyConfigOperateDrawer from '@/views/notify/scene/modules/notify-config-operate-drawer.vue'; import NotifyConfigOperateDrawer from '@/views/notify/scene/modules/notify-config-operate-drawer.vue';
import NotifyConfigSearch from '@/views/notify/scene/modules/notify-config-search.vue'; import NotifyConfigSearch from '@/views/notify/scene/modules/notify-config-search.vue';
import StatusSwitch from '@/components/common/status-switch.vue';
import { jobNotifyScene, retryNotifyScene } from '@/constants/business';
const appStore = useAppStore(); const appStore = useAppStore();
@ -48,13 +50,52 @@ const { columns, columnChecks, data, getData, loading, mobilePagination, searchP
key: 'notifyStatus', key: 'notifyStatus',
title: $t('page.notifyConfig.notifyStatus'), title: $t('page.notifyConfig.notifyStatus'),
align: 'left', align: 'left',
width: 120 width: 120,
render: row => {
const fetchFn = async (notifyStatus: Api.Common.EnableStatusNumber, callback: () => void) => {
const { error } = await fetchUpdateNotifyStatus(row.id!, notifyStatus);
if (!error) {
row.notifyStatus = notifyStatus;
window.$message?.success($t('common.updateSuccess'));
}
callback();
};
return <StatusSwitch v-model:value={row.notifyStatus} onFetch={fetchFn} />;
}
}, },
{ {
key: 'notifyScene', key: 'notifyScene',
title: $t('page.notifyConfig.notifyScene'), title: $t('page.notifyConfig.notifyScene'),
align: 'left', align: 'left',
width: 120 width: 120,
render: row => {
if (row.notifyScene === null) {
return null;
}
const tagMap: Record<number, NaiveUI.ThemeColor> = {
1: 'warning',
2: 'info',
3: 'warning',
4: 'success'
};
const index = row.notifyScene! % 4;
if (row.systemTaskType === 1) {
const label = $t(retryNotifyScene[row.notifyScene! as Api.NotifyConfig.RetryNotifyScene]);
const type = tagMap[index as Api.NotifyConfig.RetryNotifyScene];
return <NTag type={type}>{label}</NTag>;
}
if (row.systemTaskType === 3) {
const label = $t(jobNotifyScene[row.notifyScene! as Api.NotifyConfig.JobNotifyScene]);
return <NTag type={tagMap[row.notifyScene!]}>{label}</NTag>;
}
return null;
}
}, },
{ {
key: 'notifyThreshold', key: 'notifyThreshold',
@ -107,9 +148,6 @@ const {
} = useTableOperate(data, getData); } = useTableOperate(data, getData);
async function handleBatchDelete() { async function handleBatchDelete() {
// request
console.log(checkedRowKeys.value);
onBatchDeleted(); onBatchDeleted();
} }

View File

@ -3,14 +3,21 @@ import { computed, nextTick, onMounted, reactive, ref, watch } from 'vue';
import { useFormRules, useNaiveForm } from '@/hooks/common/form'; import { useFormRules, useNaiveForm } from '@/hooks/common/form';
import OperateDrawer from '@/components/common/operate-drawer.vue'; import OperateDrawer from '@/components/common/operate-drawer.vue';
import { $t } from '@/locales'; import { $t } from '@/locales';
import { fetchAddNotify, fetchEditNotify, fetchGetAllGroupNameList, fetchGetNotifyRecipientList } from '@/service/api'; import {
fetchAddNotify,
fetchEditNotify,
fetchGetJobList,
fetchGetNotifyRecipientList,
fetchGetRetrySceneList
} from '@/service/api';
import { import {
enableStatusNumberOptions, enableStatusNumberOptions,
jobNotifySceneOptions, jobNotifySceneOptions,
retryNotifySceneOptions, retryNotifySceneOptions,
systemTaskTypeOptions systemTaskTypeOptions
} from '@/constants/business'; } from '@/constants/business';
import { translateOptions, translateOptions2 } from '@/utils/common'; import { translateOptions } from '@/utils/common';
import SelectGroup from '@/components/common/select-group.vue';
defineOptions({ defineOptions({
name: 'NotifyConfigOperateDrawer' name: 'NotifyConfigOperateDrawer'
@ -23,8 +30,10 @@ interface Props {
rowData?: Api.NotifyConfig.NotifyConfig | null; rowData?: Api.NotifyConfig.NotifyConfig | null;
} }
const groupNameList = ref<string[]>([]);
const notifyRecipientList = ref<CommonType.Option<number>[]>([]); const notifyRecipientList = ref<CommonType.Option<number>[]>([]);
const retryScenes = ref<Api.RetryScene.Scene[]>([]);
const jobs = ref<Api.Job.Job[]>([]);
const props = defineProps<Props>(); const props = defineProps<Props>();
interface Emits { interface Emits {
@ -69,16 +78,10 @@ type Model = Pick<
onMounted(() => { onMounted(() => {
nextTick(() => { nextTick(() => {
getGroupNameList();
getNotifyRecipientList(); getNotifyRecipientList();
}); });
}); });
async function getGroupNameList() {
const res = await fetchGetAllGroupNameList();
groupNameList.value = res.data as string[];
}
async function getNotifyRecipientList() { async function getNotifyRecipientList() {
const res = await fetchGetNotifyRecipientList(); const res = await fetchGetNotifyRecipientList();
notifyRecipientList.value = res.data as CommonType.Option<number>[]; notifyRecipientList.value = res.data as CommonType.Option<number>[];
@ -93,7 +96,7 @@ function createDefaultModel(): Model {
notifyRecipientIds: 0, notifyRecipientIds: 0,
systemTaskType: 1, systemTaskType: 1,
notifyStatus: 1, notifyStatus: 1,
notifyScene: '', notifyScene: 1,
notifyThreshold: 0, notifyThreshold: 0,
rateLimiterStatus: 0, rateLimiterStatus: 0,
rateLimiterThreshold: 0, rateLimiterThreshold: 0,
@ -202,14 +205,25 @@ async function handleSubmit() {
emit('submitted'); emit('submitted');
} }
function systemTaskTypeChange(value: string) { async function systemTaskTypeChange(value: number) {
if (value === '1') { if (value === 1) {
const res = await fetchGetRetrySceneList({ groupName: model.groupName });
retryScenes.value = res.data as Api.RetryScene.Scene[];
options.value = translateOptions(retryNotifySceneOptions); options.value = translateOptions(retryNotifySceneOptions);
} else if (value === '3') { } else if (value === 3) {
const res = await fetchGetJobList({ groupName: model.groupName });
jobs.value = res.data as Api.Job.Job[];
options.value = translateOptions(jobNotifySceneOptions); options.value = translateOptions(jobNotifySceneOptions);
} }
model.notifyScene = ''; model.businessId = '';
model.notifyScene = 1;
}
function groupNameUpdate(groupName: string) {
handleUpdateModelWhenEdit();
model.groupName = groupName;
systemTaskTypeChange(1);
} }
watch(visible, () => { watch(visible, () => {
@ -224,12 +238,7 @@ watch(visible, () => {
<OperateDrawer v-model="visible" :title="title" @handle-submit="handleSubmit"> <OperateDrawer v-model="visible" :title="title" @handle-submit="handleSubmit">
<NForm ref="formRef" :model="model" :rules="rules"> <NForm ref="formRef" :model="model" :rules="rules">
<NFormItem :label="$t('page.notifyConfig.groupName')" path="groupName"> <NFormItem :label="$t('page.notifyConfig.groupName')" path="groupName">
<NSelect <SelectGroup v-model:modelValue="model.groupName" @update:model-value="groupNameUpdate" />
v-model:value="model.groupName"
:placeholder="$t('page.notifyConfig.form.groupName')"
:options="translateOptions2(groupNameList)"
clearable
/>
</NFormItem> </NFormItem>
<NFormItem :label="$t('page.notifyConfig.notifyStatus')" path="notifyStatus"> <NFormItem :label="$t('page.notifyConfig.notifyStatus')" path="notifyStatus">
<NRadioGroup v-model:value="model.notifyStatus" name="notifyStatus"> <NRadioGroup v-model:value="model.notifyStatus" name="notifyStatus">
@ -252,6 +261,29 @@ watch(visible, () => {
@update:value="systemTaskTypeChange" @update:value="systemTaskTypeChange"
/> />
</NFormItem> </NFormItem>
<NFormItem v-if="model.systemTaskType === 1" :label="$t('page.notifyConfig.retryScene')" path="businessId">
<NSelect
v-model:value="model.businessId"
:placeholder="$t('page.notifyConfig.form.groupName')"
:options="retryScenes"
label-field="sceneName"
value-field="sceneName"
clearable
/>
</NFormItem>
<NFormItem v-if="model.systemTaskType === 3" :label="$t('page.notifyConfig.job')" path="businessId">
<NSelect
v-model:value="model.businessId"
:placeholder="$t('page.notifyConfig.form.groupName')"
:options="jobs"
label-field="jobName"
value-field="id"
clearable
/>
</NFormItem>
<NFormItem v-if="model.systemTaskType === 4" :label="$t('page.notifyConfig.workflow')" path="businessId">
<NSelect v-model:value="model.businessId" :placeholder="$t('page.notifyConfig.form.groupName')" clearable />
</NFormItem>
<NFormItem :label="$t('page.notifyConfig.notifyScene')" path="notifyScene"> <NFormItem :label="$t('page.notifyConfig.notifyScene')" path="notifyScene">
<NSelect <NSelect
v-model:value="model.notifyScene" v-model:value="model.notifyScene"

View File

@ -6,6 +6,7 @@ import OperateDrawer from '@/components/common/operate-drawer.vue';
import { $t } from '@/locales'; import { $t } from '@/locales';
import { fetchAddUser, fetchEditUser, fetchGetAllGroupConfigList } from '@/service/api'; import { fetchAddUser, fetchEditUser, fetchGetAllGroupConfigList } from '@/service/api';
import { groupConfigYesOrNoOptions, roleRecordOptions } from '@/constants/business'; import { groupConfigYesOrNoOptions, roleRecordOptions } from '@/constants/business';
import Permission = Api.UserManager.Permission;
defineOptions({ defineOptions({
name: 'UserManagerOperateDrawer' name: 'UserManagerOperateDrawer'
@ -135,15 +136,25 @@ watch(visible, () => {
} }
}); });
function updatePermissions(p: OptionValue[]) { type PermissionModel = Pick<Permission, 'groupName' | 'namespaceId'>;
// ['snail_job_demo_group@764d604ec6fc45f68cd92514c40e9e1a']
model.permissions = p?.map(value => { function getPermission(str: string): PermissionModel {
const [groupName, namespaceId] = (value as string).split('@'); // const permissionModelComputedRef = computed<PermissionModel>(() => {
const [groupName, namespaceId] = str.split('@'); //
return { return {
groupName, groupName,
namespaceId namespaceId
}; };
}); });
return permissionModelComputedRef.value;
}
function updatePermissions(p: OptionValue[]) {
// ['snail_job_demo_group@764d604ec6fc45f68cd92514c40e9e1a']
model.permissions = p?.map(value => {
return getPermission(value as string);
});
} }
</script> </script>