From ac80d95aed88b5906c4ea2746f038a6dcf69ead2 Mon Sep 17 00:00:00 2001 From: Joel Date: Wed, 24 Jun 2026 13:42:19 +0800 Subject: [PATCH] chore: split hooks frorm agent --- .../agent-v2/agent-detail/configure/hooks.ts | 93 ++++++++++++++++++ .../agent-v2/agent-detail/configure/page.tsx | 95 +------------------ .../configure/use-agent-configure-sync.ts | 28 ++++-- 3 files changed, 114 insertions(+), 102 deletions(-) create mode 100644 web/features/agent-v2/agent-detail/configure/hooks.ts diff --git a/web/features/agent-v2/agent-detail/configure/hooks.ts b/web/features/agent-v2/agent-detail/configure/hooks.ts new file mode 100644 index 00000000000..dfdf4c7d8da --- /dev/null +++ b/web/features/agent-v2/agent-detail/configure/hooks.ts @@ -0,0 +1,93 @@ +'use client' + +import type { AgentConfigSnapshotDetailResponse, AgentSoulConfig } from '@dify/contracts/api/console/agent/types.gen' +import { skipToken, useQuery } from '@tanstack/react-query' +import { useAtom, useAtomValue } from 'jotai' +import { ModelTypeEnum } from '@/app/components/header/account-setting/model-provider-page/declarations' +import { useDefaultModel, useTextGenerationCurrentProviderAndModelAndModelList } from '@/app/components/header/account-setting/model-provider-page/hooks' +import { agentComposerAppFeaturesAtom } from '@/features/agent-v2/agent-composer/store-modules/app-features' +import { agentComposerModelAtom } from '@/features/agent-v2/agent-composer/store-modules/model' +import { consoleQuery } from '@/service/client' + +export function useAgentConfigureData(agentId: string, selectedVersionId: string | null) { + const agentQuery = useQuery(consoleQuery.agent.byAgentId.get.queryOptions({ + input: { + params: { + agent_id: agentId, + }, + }, + })) + const composerQuery = useQuery(consoleQuery.agent.byAgentId.composer.get.queryOptions({ + input: { + params: { + agent_id: agentId, + }, + }, + })) + const publishedVersionId = composerQuery.data?.active_config_snapshot?.id + const shouldLoadPublishedVersion = !selectedVersionId && !composerQuery.data?.agent_soul + const versionIdToLoad = selectedVersionId ?? (shouldLoadPublishedVersion ? publishedVersionId : undefined) + const shouldLoadVersion = !!versionIdToLoad + const versionQuery = useQuery(consoleQuery.agent.byAgentId.versions.byVersionId.get.queryOptions({ + input: versionIdToLoad + ? { + params: { + agent_id: agentId, + version_id: versionIdToLoad, + }, + } + : skipToken, + })) + const versionDetail = versionQuery.data as AgentConfigSnapshotDetailResponse | undefined + const activeVersionId = selectedVersionId ?? (shouldLoadPublishedVersion ? publishedVersionId : null) + const activeConfigSnapshot = selectedVersionId ? versionDetail : (composerQuery.data?.active_config_snapshot ?? versionDetail) + const agentSoulConfig = selectedVersionId ? versionDetail?.config_snapshot : (composerQuery.data?.agent_soul ?? versionDetail?.config_snapshot) + + return { + agentQuery, + composerQuery, + versionQuery, + shouldLoadVersion, + selectedVersionId, + activeVersionId, + activeConfigSnapshot, + agentSoulConfig, + } +} + +export function useAgentConfigureModelOptions() { + const [model, setModel] = useAtom(agentComposerModelAtom) + const { + data: defaultTextGenerationModel, + } = useDefaultModel(ModelTypeEnum.textGeneration) + const defaultModel = defaultTextGenerationModel + ? { + provider: defaultTextGenerationModel.provider.provider, + model: defaultTextGenerationModel.model, + } + : undefined + const currentModel = model ?? defaultModel + const { + textGenerationModelList, + } = useTextGenerationCurrentProviderAndModelAndModelList(currentModel) + + return { + currentModel, + setConfigureModel: setModel, + textGenerationModelList, + } +} + +export function useAgentPreviewSoulConfig( + agentSoulConfig: AgentSoulConfig | undefined, +) { + const draftAppFeatures = useAtomValue(agentComposerAppFeaturesAtom) + + if (!agentSoulConfig || !draftAppFeatures) + return agentSoulConfig + + return { + ...agentSoulConfig, + app_features: draftAppFeatures, + } +} diff --git a/web/features/agent-v2/agent-detail/configure/page.tsx b/web/features/agent-v2/agent-detail/configure/page.tsx index 1725ba145fa..ab141e1cbc1 100644 --- a/web/features/agent-v2/agent-detail/configure/page.tsx +++ b/web/features/agent-v2/agent-detail/configure/page.tsx @@ -1,23 +1,17 @@ 'use client' -import type { AgentConfigSnapshotDetailResponse, AgentIconType, AgentSoulConfig } from '@dify/contracts/api/console/agent/types.gen' -import { skipToken, useQuery } from '@tanstack/react-query' -import { useAtom, useAtomValue } from 'jotai' +import type { AgentIconType, AgentSoulConfig } from '@dify/contracts/api/console/agent/types.gen' import { useState } from 'react' import { useTranslation } from 'react-i18next' import Loading from '@/app/components/base/loading' -import { ModelTypeEnum } from '@/app/components/header/account-setting/model-provider-page/declarations' -import { useDefaultModel, useTextGenerationCurrentProviderAndModelAndModelList } from '@/app/components/header/account-setting/model-provider-page/hooks' import { AgentComposerProvider } from '@/features/agent-v2/agent-composer/provider' import { useHydrateAgentSoulConfigDraft } from '@/features/agent-v2/agent-composer/store' -import { agentComposerAppFeaturesAtom } from '@/features/agent-v2/agent-composer/store-modules/app-features' -import { agentComposerModelAtom } from '@/features/agent-v2/agent-composer/store-modules/model' -import { consoleQuery } from '@/service/client' import { AgentOrchestratePanel } from './components/orchestrate' import { AgentPreviewChat } from './components/preview/chat' import { AgentChatFeaturesPanel } from './components/preview/chat-features-panel' import { AgentPreviewHeader } from './components/preview/header' import { AgentPreviewVersionsPanel } from './components/preview/versions-panel' +import { useAgentConfigureData, useAgentConfigureModelOptions, useAgentPreviewSoulConfig } from './hooks' import { useAgentConfigureSync } from './use-agent-configure-sync' type AgentConfigurePageProps = { @@ -186,8 +180,7 @@ function AgentPreviewChatWithDraftConfig({ }: Omit[0], 'agentSoulConfig'> & { agentSoulConfig?: AgentSoulConfig }) { - const draftAppFeatures = useAtomValue(agentComposerAppFeaturesAtom) - const previewAgentSoulConfig = getPreviewAgentSoulConfig(agentSoulConfig, draftAppFeatures) + const previewAgentSoulConfig = useAgentPreviewSoulConfig(agentSoulConfig) return ( ) } - -function useAgentConfigureData(agentId: string, selectedVersionId: string | null) { - const agentQuery = useQuery(consoleQuery.agent.byAgentId.get.queryOptions({ - input: { - params: { - agent_id: agentId, - }, - }, - })) - const composerQuery = useQuery(consoleQuery.agent.byAgentId.composer.get.queryOptions({ - input: { - params: { - agent_id: agentId, - }, - }, - })) - const publishedVersionId = composerQuery.data?.active_config_snapshot?.id - const shouldLoadPublishedVersion = !selectedVersionId && !composerQuery.data?.agent_soul - const versionIdToLoad = selectedVersionId ?? (shouldLoadPublishedVersion ? publishedVersionId : undefined) - const shouldLoadVersion = !!versionIdToLoad - const versionQuery = useQuery(consoleQuery.agent.byAgentId.versions.byVersionId.get.queryOptions({ - input: versionIdToLoad - ? { - params: { - agent_id: agentId, - version_id: versionIdToLoad, - }, - } - : skipToken, - })) - const versionDetail = versionQuery.data as AgentConfigSnapshotDetailResponse | undefined - const activeVersionId = selectedVersionId ?? (shouldLoadPublishedVersion ? publishedVersionId : null) - const activeConfigSnapshot = selectedVersionId ? versionDetail : (composerQuery.data?.active_config_snapshot ?? versionDetail) - const agentSoulConfig = selectedVersionId ? versionDetail?.config_snapshot : (composerQuery.data?.agent_soul ?? versionDetail?.config_snapshot) - - return { - agentQuery, - composerQuery, - versionQuery, - shouldLoadVersion, - selectedVersionId, - activeVersionId, - activeConfigSnapshot, - agentSoulConfig, - } -} - -function useAgentConfigureModelOptions() { - const [model, setModel] = useAtom(agentComposerModelAtom) - const { - data: defaultTextGenerationModel, - } = useDefaultModel(ModelTypeEnum.textGeneration) - const defaultModel = defaultTextGenerationModel - ? { - provider: defaultTextGenerationModel.provider.provider, - model: defaultTextGenerationModel.model, - } - : undefined - const currentModel = model ?? defaultModel - const { - textGenerationModelList, - } = useTextGenerationCurrentProviderAndModelAndModelList(currentModel) - - return { - currentModel, - setConfigureModel: setModel, - textGenerationModelList, - } -} - -function getPreviewAgentSoulConfig( - agentSoulConfig: AgentSoulConfig | undefined, - draftAppFeatures: AgentSoulConfig['app_features'] | undefined, -) { - if (!agentSoulConfig || !draftAppFeatures) - return agentSoulConfig - - return { - ...agentSoulConfig, - app_features: draftAppFeatures, - } -} diff --git a/web/features/agent-v2/agent-detail/configure/use-agent-configure-sync.ts b/web/features/agent-v2/agent-detail/configure/use-agent-configure-sync.ts index ef7a769d4df..ad311d5046b 100644 --- a/web/features/agent-v2/agent-detail/configure/use-agent-configure-sync.ts +++ b/web/features/agent-v2/agent-detail/configure/use-agent-configure-sync.ts @@ -73,16 +73,24 @@ export function useAgentConfigureSync({ const composerMutation = saveStrategy === 'save_as_new_version' ? publishComposerMutation : saveComposerMutation - const composerState = await composerMutation.mutateAsync({ - params: { - agent_id: agentId, - }, - body: { - variant: 'agent_app', - save_strategy: saveStrategy, - agent_soul: configSnapshot, - }, - }) + let composerState: Awaited> + + try { + composerState = await composerMutation.mutateAsync({ + params: { + agent_id: agentId, + }, + body: { + variant: 'agent_app', + save_strategy: saveStrategy, + agent_soul: configSnapshot, + }, + }) + } + catch { + // Draft sync follows workflow autosave behavior: save failures are silent and keep the local draft intact. + return + } if (saveStrategy === 'save_to_current_version') { setOriginalDraft(agentSoulConfigToFormState(configSnapshot))