mirror of https://github.com/certd/certd
				
				
				
			perf: 增加向导
							parent
							
								
									babd5897ae
								
							
						
					
					
						commit
						6d9ef26eca
					
				|  | @ -132,6 +132,18 @@ export default function ({ crudExpose, context }: CreateCrudOptionsProps): Creat | |||
|                   } | ||||
|                 } | ||||
|               } | ||||
|             }, | ||||
|             helper: { | ||||
|               render() { | ||||
|                 const closeForm = () => { | ||||
|                   crudExpose.getFormWrapperRef().close(); | ||||
|                 }; | ||||
|                 return ( | ||||
|                   <router-link to={"/sys/cname/provider"} onClick={closeForm}> | ||||
|                     前往设置CNAME服务 | ||||
|                   </router-link> | ||||
|                 ); | ||||
|               } | ||||
|             } | ||||
|           }, | ||||
|           column: { | ||||
|  |  | |||
|  | @ -1,7 +1,12 @@ | |||
| <template> | ||||
|   <fs-page class="page-cert"> | ||||
|     <template #header> | ||||
|       <div class="title">CNAME记录管理</div> | ||||
|       <div class="title"> | ||||
|         CNAME记录管理 | ||||
|         <span class="sub"> | ||||
|           <a href="https://certd.docmirror.cn/guide/feature/cname/" target="_blank">CNAME功能原理及使用说明</a> | ||||
|         </span> | ||||
|       </div> | ||||
|     </template> | ||||
|     <fs-crud ref="crudRef" v-bind="crudBinding"> | ||||
|       <template #pagination-left> | ||||
|  |  | |||
|  | @ -1,79 +1,127 @@ | |||
| <template> | ||||
|   <fs-page class="fs-pipeline-detail"> | ||||
|     <pipeline-edit v-model:edit-mode="editMode" :pipeline-id="pipelineId" :options="pipelineOptionsRef"></pipeline-edit> | ||||
|     <a-tour v-model:current="tourCurrent" :open="tourOpen" :steps="tourSteps" @close="tourHandleOpen(false)" /> | ||||
|   </fs-page> | ||||
| </template> | ||||
| 
 | ||||
| <script lang="ts"> | ||||
| import { defineComponent, Ref, ref } from "vue"; | ||||
| <script lang="ts" setup> | ||||
| import { nextTick, onMounted, Ref, ref } from "vue"; | ||||
| import PipelineEdit from "./pipeline/index.vue"; | ||||
| import * as pluginApi from "./api.plugin"; | ||||
| import * as historyApi from "./api.history"; | ||||
| import * as api from "./api"; | ||||
| import { useRoute } from "vue-router"; | ||||
| import { PipelineDetail, PipelineOptions, PluginGroups, RunHistory } from "./pipeline/type"; | ||||
| import { TourProps } from "ant-design-vue"; | ||||
| 
 | ||||
| export default defineComponent({ | ||||
|   name: "PipelineDetail", | ||||
|   components: { PipelineEdit }, | ||||
|   setup() { | ||||
|     const route = useRoute(); | ||||
|     const pipelineId: Ref = ref(route.query.id); | ||||
| 
 | ||||
|     const pipelineOptions: PipelineOptions = { | ||||
|       async getPipelineDetail({ pipelineId }) { | ||||
|         const detail = await api.GetDetail(pipelineId); | ||||
|         return { | ||||
|           pipeline: { | ||||
|             id: detail.pipeline.id, | ||||
|             stages: [], | ||||
|             triggers: [], | ||||
|             ...JSON.parse(detail.pipeline.content || "{}") | ||||
|           } | ||||
|         } as PipelineDetail; | ||||
|       }, | ||||
| 
 | ||||
|       async getHistoryList({ pipelineId }) { | ||||
|         const list: RunHistory[] = await historyApi.GetList({ pipelineId }); | ||||
|         return list; | ||||
|       }, | ||||
| 
 | ||||
|       async getHistoryDetail({ historyId }): Promise<RunHistory> { | ||||
|         const detail = await historyApi.GetDetail({ id: historyId }); | ||||
|         return detail; | ||||
|       }, | ||||
| 
 | ||||
|       async getPluginGroups() { | ||||
|         const groups = await pluginApi.GetGroups({}); | ||||
|         return new PluginGroups(groups); | ||||
|       }, | ||||
| 
 | ||||
|       async doSave(pipelineConfig: any) { | ||||
|         await api.Save({ | ||||
|           id: pipelineConfig.id, | ||||
|           content: JSON.stringify(pipelineConfig) | ||||
|         }); | ||||
|       }, | ||||
|       async doTrigger(options: { pipelineId: number; stepId?: string }) { | ||||
|         const { pipelineId, stepId } = options; | ||||
|         await api.Trigger(pipelineId, stepId); | ||||
|       } | ||||
|     }; | ||||
| 
 | ||||
|     const pipelineOptionsRef: Ref<PipelineOptions> = ref(pipelineOptions); | ||||
| 
 | ||||
|     const editMode = ref(false); | ||||
|     if (route.query.editMode !== "false") { | ||||
|       editMode.value = true; | ||||
|     } | ||||
| 
 | ||||
|     return { | ||||
|       pipelineOptionsRef, | ||||
|       pipelineId, | ||||
|       editMode | ||||
|     }; | ||||
|   } | ||||
| defineOptions({ | ||||
|   name: "PipelineDetail" | ||||
| }); | ||||
| const route = useRoute(); | ||||
| const pipelineId: Ref = ref(route.query.id); | ||||
| 
 | ||||
| const pipelineOptions: PipelineOptions = { | ||||
|   async getPipelineDetail({ pipelineId }) { | ||||
|     const detail = await api.GetDetail(pipelineId); | ||||
|     onLoaded(); | ||||
|     return { | ||||
|       pipeline: { | ||||
|         id: detail.pipeline.id, | ||||
|         stages: [], | ||||
|         triggers: [], | ||||
|         ...JSON.parse(detail.pipeline.content || "{}") | ||||
|       } | ||||
|     } as PipelineDetail; | ||||
|   }, | ||||
| 
 | ||||
|   async getHistoryList({ pipelineId }) { | ||||
|     const list: RunHistory[] = await historyApi.GetList({ pipelineId }); | ||||
|     return list; | ||||
|   }, | ||||
| 
 | ||||
|   async getHistoryDetail({ historyId }): Promise<RunHistory> { | ||||
|     const detail = await historyApi.GetDetail({ id: historyId }); | ||||
|     return detail; | ||||
|   }, | ||||
| 
 | ||||
|   async getPluginGroups() { | ||||
|     const groups = await pluginApi.GetGroups({}); | ||||
|     return new PluginGroups(groups); | ||||
|   }, | ||||
| 
 | ||||
|   async doSave(pipelineConfig: any) { | ||||
|     await api.Save({ | ||||
|       id: pipelineConfig.id, | ||||
|       content: JSON.stringify(pipelineConfig) | ||||
|     }); | ||||
|   }, | ||||
|   async doTrigger(options: { pipelineId: number; stepId?: string }) { | ||||
|     const { pipelineId, stepId } = options; | ||||
|     await api.Trigger(pipelineId, stepId); | ||||
|   } | ||||
| }; | ||||
| 
 | ||||
| const pipelineOptionsRef: Ref<PipelineOptions> = ref(pipelineOptions); | ||||
| 
 | ||||
| const editMode = ref(false); | ||||
| if (route.query.editMode !== "false") { | ||||
|   editMode.value = true; | ||||
| } | ||||
| 
 | ||||
| function useTour() { | ||||
|   const tourOpen = ref<boolean>(false); | ||||
| 
 | ||||
|   const tourCurrent = ref(0); | ||||
|   //@ts-ignore | ||||
|   const tourSteps: TourProps["steps"] = ref([]); | ||||
| 
 | ||||
|   const tourHandleOpen = (val: boolean): void => { | ||||
|     initSteps(); | ||||
|     tourOpen.value = val; | ||||
|   }; | ||||
| 
 | ||||
|   function initSteps() { | ||||
|     //@ts-ignore | ||||
|     tourSteps.value = [ | ||||
|       { | ||||
|         title: "恭喜创建证书流水线成功", | ||||
|         description: "这里就是我们刚创建的证书任务,点击可以修改证书申请参数", | ||||
|         target: () => { | ||||
|           return document.querySelector(".pipeline .stages .stage_0 .task"); | ||||
|         } | ||||
|       }, | ||||
|       { | ||||
|         title: "添加部署证书任务", | ||||
|         description: "证书申请成功之后还需要部署证书,点击这里可以添加部署任务", | ||||
|         target: () => { | ||||
|           return document.querySelector(".pipeline .stages .last-stage .tasks .task"); | ||||
|         } | ||||
|       }, | ||||
|       { | ||||
|         title: "手动运行流水线", | ||||
|         description: "点击此处可以手动运行流水线", | ||||
|         target: () => { | ||||
|           return document.querySelector(".pipeline .stages .first-stage .tasks .task"); | ||||
|         } | ||||
|       } | ||||
|     ]; | ||||
|   } | ||||
| 
 | ||||
|   return { | ||||
|     tourOpen, | ||||
|     tourCurrent, | ||||
|     tourSteps, | ||||
|     tourHandleOpen | ||||
|   }; | ||||
| } | ||||
| 
 | ||||
| const { tourOpen, tourCurrent, tourSteps, tourHandleOpen } = useTour(); | ||||
| 
 | ||||
| async function onLoaded() { | ||||
|   await nextTick(); | ||||
|   tourHandleOpen(true); | ||||
| } | ||||
| </script> | ||||
| <style lang="less"> | ||||
| .page-pipeline-detail { | ||||
|  |  | |||
|  | @ -66,7 +66,7 @@ | |||
|               </template> | ||||
| 
 | ||||
|               <template #item="{ element: stage, index }"> | ||||
|                 <div :key="stage.id" class="stage" :class="{ 'last-stage': isLastStage(index) }"> | ||||
|                 <div :key="stage.id" class="stage" :class="{ 'last-stage': isLastStage(index), ['stage_' + index]: true }"> | ||||
|                   <div class="title"> | ||||
|                     <text-editable v-model="stage.title" :disabled="!editMode"></text-editable> | ||||
|                     <div v-plus class="icon-box stage-move-handle"> | ||||
|  | @ -252,7 +252,7 @@ | |||
| </template> | ||||
| 
 | ||||
| <script lang="ts"> | ||||
| import { defineComponent, ref, provide, Ref, watch } from "vue"; | ||||
| import { defineComponent, ref, provide, Ref, watch, onMounted } from "vue"; | ||||
| import { useRouter } from "vue-router"; | ||||
| import PiTaskForm from "./component/task-form/index.vue"; | ||||
| import PiTriggerForm from "./component/trigger-form/index.vue"; | ||||
|  | @ -261,7 +261,7 @@ import PiTaskView from "./component/task-view/index.vue"; | |||
| import PiStatusShow from "./component/status-show.vue"; | ||||
| import VDraggable from "vuedraggable"; | ||||
| import _ from "lodash-es"; | ||||
| import { message, Modal, notification } from "ant-design-vue"; | ||||
| import { message, Modal, notification, TourProps } from "ant-design-vue"; | ||||
| import { nanoid } from "nanoid"; | ||||
| import { PipelineDetail, PipelineOptions, PluginGroups, RunHistory } from "./type"; | ||||
| import type { Runnable, Stage } from "@certd/pipeline"; | ||||
|  |  | |||
|  | @ -21,9 +21,12 @@ | |||
|       <div class="suggest"> | ||||
|         <div> | ||||
|           <tutorial-button class="flex-center"> | ||||
|             <a-tag color="blue" class="flex-center"> | ||||
|               仅需3步,全自动申请部署证书<fs-icon class="font-size-16 ml-5" icon="mingcute:question-line"></fs-icon | ||||
|             ></a-tag> | ||||
|             <a-tooltip title="点击查看详细教程"> | ||||
|               <a-tag color="blue" class="flex-center"> | ||||
|                 仅需3步,全自动申请部署证书 | ||||
|                 <fs-icon class="font-size-16 ml-5" icon="mingcute:question-line"></fs-icon> | ||||
|               </a-tag> | ||||
|             </a-tooltip> | ||||
|           </tutorial-button> | ||||
|           <simple-steps></simple-steps> | ||||
|         </div> | ||||
|  | @ -79,7 +82,7 @@ | |||
|           支持的部署任务列表 <a-tag color="green">{{ pluginGroups.groups.all.plugins.length }}</a-tag> | ||||
|         </template> | ||||
|         <a-row :gutter="10"> | ||||
|           <a-col v-for="item of pluginGroups.groups.all.plugins" class="plugin-item-col" :span="4"> | ||||
|           <a-col v-for="item of pluginGroups.groups.all.plugins" :key="item.name" class="plugin-item-col" :span="4"> | ||||
|             <a-card> | ||||
|               <a-tooltip :title="item.desc"> | ||||
|                 <div class="plugin-item pointer"> | ||||
|  | @ -165,7 +168,7 @@ function transformStatusCount() { | |||
| async function loadCount() { | ||||
|   count.value = await GetStatisticCount(); | ||||
|   transformStatusCount(); | ||||
|   count.value.historyCountPerDay = count.value.historyCountPerDay.map((item) => { | ||||
|   count.value.historyCountPerDay = count.value.historyCountPerDay.map((item: any) => { | ||||
|     return { | ||||
|       name: item.date, | ||||
|       value: item.count | ||||
|  |  | |||
|  | @ -5,7 +5,7 @@ | |||
|         CNAME服务配置 | ||||
|         <span class="sub"> | ||||
|           此处配置的域名作为其他域名校验的代理,当别的域名需要申请证书时,通过CNAME映射到此域名上来验证所有权。好处是任何域名都可以通过此方式申请证书,也无需填写AccessSecret。 | ||||
|           <a href="https://certd.docmirror.cn/guide/feature/cname/" taget="_blank">CNAME功能原理及使用说明</a> | ||||
|           <a href="https://certd.docmirror.cn/guide/feature/cname/" target="_blank">CNAME功能原理及使用说明</a> | ||||
|         </span> | ||||
|       </div> | ||||
|     </template> | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue
	
	 xiaojunnuo
						xiaojunnuo