搜索结果列表页面开发
This commit is contained in:
224
src/components/Setting/WebHookEdit/Index.vue
Normal file
224
src/components/Setting/WebHookEdit/Index.vue
Normal file
@@ -0,0 +1,224 @@
|
||||
<script setup lang="ts">
|
||||
import { reactive, ref, toRaw, watchEffect } from 'vue';
|
||||
import { customEventList } from './customEventList';
|
||||
import { useRouter } from 'vue-router';
|
||||
import debounce from 'lodash/debounce';
|
||||
import { urlRegExp } from '@/utils/regex';
|
||||
const emits = defineEmits(['create', 'change']);
|
||||
const nameMaxLen = 500;
|
||||
const props = defineProps<{
|
||||
data?: Record<string, any>;
|
||||
editable?: boolean;
|
||||
loading?: boolean;
|
||||
}>();
|
||||
const router = useRouter();
|
||||
const formRef = ref<any>(null);
|
||||
const form = reactive<Record<string, any>>({
|
||||
url: '',
|
||||
push_events: true,
|
||||
tag_push_events: false,
|
||||
merge_requests_events: false,
|
||||
note_events: false,
|
||||
content_type: 'application/json',
|
||||
token: '',
|
||||
active: true
|
||||
});
|
||||
|
||||
const hookToken = ref('');
|
||||
|
||||
type WebHookEventKey = keyof typeof form
|
||||
|
||||
const contentTypeList = ref(['application/json', 'application/x-www-form-urlencoded']);
|
||||
|
||||
// const eventTypeList = shallowRef<{ key: WebHookEventKey, label: string }[]>([
|
||||
// // {
|
||||
// // key: 'all',
|
||||
// // label: '全部事件'
|
||||
// // },
|
||||
// {
|
||||
// key: 'push_events',
|
||||
// label: '仅限 push 事件'
|
||||
// },
|
||||
// {
|
||||
// key: 'custom_ctrl_item_events',
|
||||
// label: '自定义事件'
|
||||
// }
|
||||
// ]);
|
||||
|
||||
const handleClick = async() => {
|
||||
const valid = await formRef.value.validate();
|
||||
if (valid) {
|
||||
if (props?.editable) {
|
||||
const { token, ...config } = toRaw(form);
|
||||
if (token) {
|
||||
emits('change', { token, ...config });
|
||||
} else {
|
||||
emits('change', config);
|
||||
}
|
||||
} else {
|
||||
emits('create', toRaw(form));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const handleCancel = () => {
|
||||
router.back();
|
||||
};
|
||||
|
||||
const regex = /^[^\*\u4e00-\u9fa5\s]*$/;
|
||||
|
||||
const handleChange = (val: string) => {
|
||||
if (props.editable) {
|
||||
form.token = val;
|
||||
}
|
||||
};
|
||||
|
||||
const handleFocus = () => {
|
||||
if (props.editable) {
|
||||
if (!form.token) {
|
||||
hookToken.value = '';
|
||||
} else {
|
||||
hookToken.value = form.token;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const handleBlur = () => {
|
||||
if (props.editable) {
|
||||
if (!form.token) {
|
||||
hookToken.value = props?.data?.token ? '*'.repeat(props.data.token.length) : '********';
|
||||
} else {
|
||||
hookToken.value = form.token;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const handleInput = debounce((val: string) => {
|
||||
if (val && formRef.value) {
|
||||
form.token = val;
|
||||
if (regex.test(val) && val.length <= 2000) {
|
||||
formRef.value.clearValidate(['token']);
|
||||
} else {
|
||||
formRef.value.validateFields(['token']);
|
||||
}
|
||||
}
|
||||
}, 500);
|
||||
|
||||
watchEffect(() => {
|
||||
if (props.data) {
|
||||
for (const key in form) {
|
||||
if (key === 'token' && props.editable) {
|
||||
form.token = '';
|
||||
hookToken.value = props?.data?.token ? '*'.repeat(props.data.token.length) : '********';
|
||||
} else {
|
||||
form[key] = props.data[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
function restricVal(event:any) {
|
||||
let value = event.target.value;
|
||||
if (event.type === 'paste') value = (event.clipboardData || (window as any).clipboardData).getData('text');
|
||||
if (value.length < nameMaxLen) return;
|
||||
form.url = value.slice(0, nameMaxLen);
|
||||
event.preventDefault();
|
||||
}
|
||||
const formRules = { // 表单校验
|
||||
url: [
|
||||
{ required: true, message: '请填写WebHook的url信息', trigger: 'blur' },
|
||||
{ max: nameMaxLen, message: 'WebHook的url信息长度不能超过500' },
|
||||
{ message: '请输入正确的URL地址', pattern: urlRegExp },
|
||||
],
|
||||
content_type: [{ required: true, message: '请选择POST请求内容类型', trigger: 'blur' }],
|
||||
token: [
|
||||
{ required: !props.editable, message: '请输入Token', trigger: 'blur' },
|
||||
{ message: 'Token不能包含中文、空格、*', pattern: regex },
|
||||
{ max: 2000, message: 'WebHook的Token信息长度不能超过2000' }
|
||||
]
|
||||
};
|
||||
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="web-hook-edit g-content-card p-20">
|
||||
<d-form class="max-w-[900px]" :pop-position="['right']" :data="form" layout="vertical" ref="formRef" :rules="formRules">
|
||||
<d-form-item field="url" label="URL">
|
||||
<d-input maxlength="500" v-model="form.url" placeholder="请输入 WebHook 的 URL 地址" v-on:keypress="restricVal" v-on:paste="restricVal">
|
||||
<template #suffix><span>{{form.url?.length}}/{{ nameMaxLen }}</span></template>
|
||||
</d-input>
|
||||
</d-form-item>
|
||||
<d-form-item field="token" label="Token">
|
||||
<div v-if="editable">
|
||||
<div class="text-CG600 text-[14px] mb-[10px]">
|
||||
如果你忘记了之前设置的Token, 你可以重新添加添加一个Token, 为避免影响正常使用, 请将所有应用到该Token的配置更新为最新的Token。
|
||||
</div>
|
||||
<d-input maxlength="2000" placeholder="请输入Token" v-model="hookToken" @change="handleChange" @focus="handleFocus" @blur="handleBlur" @input="handleInput">
|
||||
<template #suffix><span>{{hookToken?.length}}/2000</span></template>
|
||||
</d-input>
|
||||
</div>
|
||||
<d-input maxlength="2000" placeholder="请输入Token" v-model="form.token" v-else>
|
||||
<template #suffix><span>{{form.token?.length}}/2000</span></template>
|
||||
</d-input>
|
||||
</d-form-item>
|
||||
<d-form-item field="content_type" class="no-label">
|
||||
<div class="flex items-center">
|
||||
<div class="text-G900 mr-[10px]">POST 请求内容类型</div>
|
||||
<d-select
|
||||
class="web-hook-select"
|
||||
v-model="form.content_type"
|
||||
:placeholder="form.content_type"
|
||||
>
|
||||
<gc-option v-for="(item,index) of contentTypeList.filter(name => name !== form.content_type)" :key="index" :value="item" :title="item">
|
||||
<span>{{ item }}</span>
|
||||
</gc-option>
|
||||
</d-select>
|
||||
</div>
|
||||
</d-form-item>
|
||||
|
||||
<div class="my-[10px]">事件类型</div>
|
||||
|
||||
<div class="webhook-checkbox flex flex-wrap">
|
||||
<d-checkbox class="my-[10px] w-[25%]" v-for="item of customEventList" :key="item.key" v-model="form[item.key as WebHookEventKey]">{{ item.title }}</d-checkbox>
|
||||
</div>
|
||||
|
||||
<d-checkbox class="my-[10px]" v-model="form.active">
|
||||
<span class="inline-block mr-[1px]">激活</span>
|
||||
<span class="text-G600">(当以上指定事件触发时将发送请求)</span>
|
||||
</d-checkbox>
|
||||
<div class="flex items-center mt-5 justify-end">
|
||||
<d-button class="mr-4 w-[64px]" @click="handleCancel"><span>取消</span></d-button>
|
||||
<d-button variant="solid" :loading="loading" @click="handleClick">{{ editable ? '保存' : ' 创建' }}</d-button>
|
||||
</div>
|
||||
</d-form>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="scss">
|
||||
.web-hook-edit {
|
||||
.web-hook-select {
|
||||
width: 320px;
|
||||
input::placeholder {
|
||||
color: var(--color-G900);
|
||||
}
|
||||
}
|
||||
.webhook-checkbox {
|
||||
.devui-checkbox label>span.devui-checkbox__label-text {
|
||||
line-height: 18px;
|
||||
}
|
||||
}
|
||||
.devui-form__item--vertical {
|
||||
margin-bottom: 10px;
|
||||
&:nth-of-type(3) {
|
||||
.devui-form__label--vertical {
|
||||
height: 0;
|
||||
padding-bottom: 10px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.no-label{
|
||||
:deep(.devui-form__label){
|
||||
display:none;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
92
src/components/Setting/WebHookEdit/customEventList.ts
Normal file
92
src/components/Setting/WebHookEdit/customEventList.ts
Normal file
@@ -0,0 +1,92 @@
|
||||
export const customEventList = [
|
||||
{
|
||||
key: 'push_events',
|
||||
title: '推送事件'
|
||||
},
|
||||
{
|
||||
key: 'merge_requests_events',
|
||||
title: 'Pull Request事件'
|
||||
// desc: '合并请求请求事件,包括合并请求的新建、分配负责人、取消负责人、关闭、转换成草稿(WIP)、新增 Label、移除 Label、新增里程碑、移除里程碑、重新打开事件'
|
||||
},
|
||||
{
|
||||
key: 'tag_push_events',
|
||||
title: 'Tag推送事件'
|
||||
},
|
||||
{
|
||||
key: 'note_events',
|
||||
title: '评论事件'
|
||||
// desc: '新建分支或新建 Tag'
|
||||
}
|
||||
// {
|
||||
// title: '删除分支或 Tag',
|
||||
// desc: '删除分支或删除 Tag'
|
||||
// },
|
||||
// {
|
||||
// title: '保护分支更新',
|
||||
// desc: '新增、删除或修改保护分支设置'
|
||||
// },
|
||||
// {
|
||||
// title: 'Forks',
|
||||
// desc: '项目的 Fork 事件'
|
||||
// },
|
||||
// {
|
||||
// title: '项目成员更新',
|
||||
// desc: '新增、移除项目成员,或项目成员权限变更'
|
||||
// },
|
||||
// {
|
||||
// title: 'Star',
|
||||
// desc: '项目新增 Star 或取消 Star'
|
||||
// },
|
||||
// {
|
||||
// key: 'issues_events',
|
||||
// title: 'Issues',
|
||||
// desc: 'Issues 事件,包括 Issue 的新增,编辑、删除、转移、置顶、取消置顶、关闭、重新打开、分配负责人、取消负责人、新增 Label、移除 Label、新增里程碑、移除里程碑、锁定和取消锁定事件'
|
||||
// },
|
||||
// {
|
||||
// title: '提交评论',
|
||||
// desc: '提交或 Diff 的评论事件'
|
||||
// },
|
||||
// {
|
||||
// title: '里程碑',
|
||||
// desc: '里程碑事件,包括里程碑的新增、关闭、打开、编辑和删除事件'
|
||||
// },
|
||||
// {
|
||||
// title: '看板',
|
||||
// desc: '新增、更新和删除看板'
|
||||
// },
|
||||
// {
|
||||
// title: 'Pages',
|
||||
// desc: 'Pages 站点更新'
|
||||
// },
|
||||
// {
|
||||
// title: '看板事件',
|
||||
// desc: '看板内容更新事件,包括新增、编辑、删除、归档、恢复、转换成 Issue 和排序'
|
||||
// },
|
||||
// {
|
||||
// key: 'push_events',
|
||||
// title: 'push 事件',
|
||||
// desc: '代码库的 git push 事件'
|
||||
// },
|
||||
// {
|
||||
// key: 'change_request_events',
|
||||
// title: '合并请求评审状态事件',
|
||||
// desc: '合并请求的代码评审事件(评审通过/不通过相关)'
|
||||
// },
|
||||
// {
|
||||
// title: '代码评审评论',
|
||||
// desc: '代码评审的评论事件'
|
||||
// },
|
||||
// {
|
||||
// key: 'wiki_page_events',
|
||||
// title: 'Wiki',
|
||||
// desc: 'Wiki 更新'
|
||||
// }
|
||||
// {
|
||||
// title: '项目导入',
|
||||
// desc: '项目导入成功、失败或取消'
|
||||
// },
|
||||
// {
|
||||
// title: '公开项目',
|
||||
// desc: '项目由私密项目更改为公开项目'
|
||||
// }
|
||||
];
|
||||
Reference in New Issue
Block a user