| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196 |
- <template>
- <el-popover
- ref="popoverRef"
- width="300px"
- trigger="click"
- placement="bottom-end"
- :disabled="isPublishing"
- >
- <div class="publish-selector">
- <div class="publish-selector__title">{{ t('pages.editor.selectPublishNode') }}</div>
- <div class="flex items-center gap-2">
- <el-input v-model="search" placeholder="搜索" />
- </div>
- <el-divider class="my-0" />
- <el-scrollbar height="280px">
- <button
- v-for="node in publishNodes"
- :key="node.id"
- type="button"
- class="publish-selector__item"
- @click="handleSelectPublishNode(node.id)"
- >
- <span class="flex items-center gap-1">
- <Icon
- :icon="nodeMap[node.nodeType]?.icon!"
- :color="nodeMap[node.nodeType]?.iconColor"
- :size="18"
- />
- <span class="publish-selector__name">{{ node.name }}</span>
- </span>
- <span class="publish-selector__type">{{ nodeMap[node.nodeType]?.displayName }}</span>
- </button>
- <el-empty v-if="!publishNodes.length" :image-size="120" description="无节点数据" />
- </el-scrollbar>
- </div>
- <template #reference>
- <el-button
- :type="isPublished ? 'success' : 'default'"
- size="small"
- :disabled="!publishNodes.length"
- :loading="isPublishing"
- @click="handlePublishClick"
- >
- <Icon v-if="isPublished" icon="ix:success" class="mr-1" />
- {{
- isPublished ? t('pages.editor.status.published') : t('pages.editor.status.unpublished')
- }}
- </el-button>
- </template>
- </el-popover>
- </template>
- <script setup lang="ts">
- import { computed, ref } from 'vue'
- import { ElMessage, type PopoverInstance } from 'element-plus'
- import { agent } from '@repo/api-service'
- import { Icon } from '@repo/ui'
- import type { IWorkflow } from '@repo/workflow'
- import { useI18n } from '@/composables/useI18n'
- import { nodeMap } from '@/nodes'
- const props = defineProps<{
- workflow: IWorkflow
- }>()
- const emit = defineEmits<{
- (e: 'published'): void
- }>()
- const { t } = useI18n()
- const popoverRef = ref<PopoverInstance>()
- const isPublishing = ref(false)
- const search = ref('')
- // const PUBLISHABLE_NODE_TYPES = ['start', 'trigger-schedule', 'trigger-webhook']
- const isPublished = computed(() => props.workflow?.status === 'published')
- const publishNodes = computed(() => {
- return (
- (props.workflow?.nodes || [])
- // .filter((node) => {
- // const nodeType = (node as any)?.nodeType || (node as any)?.data?.nodeType
- // return PUBLISHABLE_NODE_TYPES.includes(nodeType || '')
- // })
- .filter((node) => node.name?.includes(search.value))
- .map((node) => {
- const nodeType = ((node as any)?.nodeType || (node as any)?.data?.nodeType || '') as string
- return {
- id: node.id,
- name: node.name || nodeType,
- nodeType
- }
- })
- )
- })
- const publishAgent = async (nodeId?: string) => {
- if (!nodeId) {
- ElMessage.warning(t('pages.editor.messages.missingPublishNode'))
- return
- }
- if (isPublishing.value) {
- return
- }
- isPublishing.value = true
- try {
- const response = await agent.postAgentDoAgentPublish({
- start_node_id: nodeId,
- appAgentId: props.workflow.id
- })
- if (response?.isSuccess) {
- props.workflow.status = 'published'
- popoverRef.value?.hide()
- ElMessage.success(t('pages.editor.messages.publishSuccess'))
- emit('published')
- return
- }
- if ((response as any)?.error) {
- ElMessage.error((response as any).error)
- return
- }
- ElMessage.error(t('pages.editor.messages.publishFailed'))
- } catch (error) {
- console.error('postAgentDoAgentPublish error', error)
- ElMessage.error(t('pages.editor.messages.publishFailed'))
- } finally {
- isPublishing.value = false
- }
- }
- const handlePublishClick = () => {
- if (publishNodes.value.length <= 1) {
- publishAgent(publishNodes.value[0]?.id)
- }
- }
- const handleSelectPublishNode = (id: string) => {
- publishAgent(id)
- }
- </script>
- <style scoped>
- .publish-selector {
- display: flex;
- flex-direction: column;
- gap: 8px;
- }
- .publish-selector__title {
- font-size: 13px;
- font-weight: 600;
- color: #344054;
- }
- .publish-selector__item {
- display: flex;
- align-items: center;
- justify-content: space-between;
- gap: 12px;
- width: 100%;
- padding: 10px 12px;
- border: 1px solid #e4e7ec;
- border-radius: 10px;
- background: #fff;
- cursor: pointer;
- text-align: left;
- margin-bottom: 8px;
- }
- .publish-selector__item:hover {
- border-color: #2563eb;
- background: #f8fbff;
- }
- .publish-selector__name {
- font-size: 13px;
- font-weight: 500;
- color: #344054;
- }
- .publish-selector__type {
- font-size: 12px;
- color: #667085;
- }
- </style>
|