import { addApp, apiInterceptors, getAgents, getResourceType, getTeamMode, updateApp } from '@/client/api'; import { AgentParams, CreateAppParams, IAgent as IAgentParams, IDetail } from '@/types/app'; import { IFlow } from '@/types/flow'; import type { TabsProps } from 'antd'; import { Dropdown, Form, Input, Modal, Select, Space, Spin, Tabs } from 'antd'; import React, { useEffect, useState } from 'react'; import { useTranslation } from 'react-i18next'; import AddIcon from '../icons/add-icon'; import AgentPanel from './agent-panel'; import DagLayout from './dag-layout'; type TargetKey = string; type FieldType = { app_name: string; app_describe: string; language: string; team_mode: string; }; type IAgent = { label: string; children?: React.ReactNode; onClick?: () => void; key: number | string; }; interface IProps { handleCancel: () => void; open: boolean; updateApps: () => void; type: string; app?: any; } type TeamModals = 'awel_layout' | 'singe_agent' | 'auto_plan'; export default function AppModal(props: IProps) { const { handleCancel, open, updateApps, type, app } = props; const { t } = useTranslation(); const [spinning, setSpinning] = useState(false); const [activeKey, setActiveKey] = useState(); const [teamModal, setTeamModal] = useState<{ label: string; value: string }[]>(); const [agents, setAgents] = useState([]); const [dropItems, setDropItems] = useState([]); const [details, setDetails] = useState([...(app?.details || [])]); const [flow, setFlow] = useState(); const [resourceTypes, setResourceTypes] = useState(); const [curTeamModal, setCurTeamModal] = useState(app.team_modal || 'auto_plan'); const [form] = Form.useForm(); const languageOptions = [ { value: 'zh', label: t('Chinese') }, { value: 'en', label: t('English') }, ]; const onChange = (newActiveKey: string) => { setActiveKey(newActiveKey); }; const createApp = async (app: CreateAppParams) => { await apiInterceptors(type === 'add' ? addApp(app) : updateApp(app)); await updateApps(); }; const initApp = async () => { const appDetails = app.details; const [_, resourceType] = await apiInterceptors(getResourceType()); if (appDetails?.length > 0) { setAgents( appDetails?.map((item: AgentParams) => { return { label: item?.agent_name, children: ( ), key: item?.agent_name, }; }), ); } }; const fetchTeamModal = async () => { const [_, data] = await apiInterceptors(getTeamMode()); if (!data) return null; const teamModalOptions = data.map(item => { return { value: item, label: item }; }); setTeamModal(teamModalOptions); }; const fetchAgent = async () => { const [_, data] = await apiInterceptors(getAgents()); if (!data) { return null; } setDropItems( data .map(agent => { return { label: agent.name, key: agent.name, onClick: () => { add(agent); }, agent, }; }) .filter(item => { if (!app.details || app.details?.length === 0) { return item; } return app?.details?.every((detail: AgentParams) => detail.agent_name !== item.label); }), ); }; const handleFlowsChange = (data: IFlow) => { setFlow(data); }; const fetchResourceType = async () => { const [_, data] = await apiInterceptors(getResourceType()); if (data) { setResourceTypes(data); } }; useEffect(() => { fetchTeamModal(); fetchAgent(); fetchResourceType(); }, []); useEffect(() => { type === 'edit' && initApp(); }, [resourceTypes]); useEffect(() => { setCurTeamModal(app.team_mode || 'auto_plan'); }, [app]); const updateDetailsByAgentKey = (key: string, data: IDetail) => { setDetails((details: IDetail[]) => { return details.map((detail: IDetail) => { return key === (detail.agent_name || detail.key) ? data : detail; }); }); }; const add = async (tabBar: IAgentParams) => { const newActiveKey = tabBar.name; const [_, data] = await apiInterceptors(getResourceType()); setActiveKey(newActiveKey); setDetails((details: IDetail[]) => { return [...details, { key: newActiveKey, name: '', llm_strategy: 'priority' }]; }); setAgents((items: any) => { return [ ...items, { label: newActiveKey, children: ( ), key: newActiveKey, }, ]; }); setDropItems(items => { return items.filter(item => item.key !== tabBar.name); }); }; const remove = (targetKey: TargetKey) => { let newActiveKey = activeKey; let lastIndex = -1; if (!agents) { return null; } agents.forEach((item, i) => { if (item.key === targetKey) { lastIndex = i - 1; } }); const newPanes = agents.filter(item => item.key !== targetKey); if (newPanes.length && newActiveKey === targetKey) { if (lastIndex >= 0) { newActiveKey = newPanes[lastIndex].key; } else { newActiveKey = newPanes[0].key; } } setDetails((details: IDetail[]) => { return details?.filter((detail: any) => { return (detail.agent_name || detail.key) !== targetKey; }); }); setAgents(newPanes); setActiveKey(newActiveKey); setDropItems((items: any) => { return [ ...items, { label: targetKey, key: targetKey, onClick: () => { add({ name: targetKey, describe: '', system_message: '' }); }, }, ]; }); }; const onEdit = (targetKey: any, action: 'add' | 'remove') => { if (action === 'add') { // add(); } else { remove(targetKey); } }; const handleSubmit = async () => { const isValidate = await form.validateFields(); if (!isValidate) { return; } setSpinning(true); const data = { ...form.getFieldsValue(), }; if (type === 'edit') { data.app_code = app.app_code; } if (data.team_mode !== 'awel_layout') { data.details = details; } else { const tempFlow = { ...flow }; delete tempFlow.flow_data; data.team_context = tempFlow; } try { await createApp(data); } catch { return; } setSpinning(false); handleCancel(); }; const handleTeamModalChange = (value: TeamModals) => { setCurTeamModal(value); }; const renderAddIcon = () => { return ( e.preventDefault()}> ); }; return (
label={'App Name'} name='app_name' rules={[{ required: true, message: t('Please_input_the_name') }]} > label={t('Description')} name='app_describe' rules={[{ required: true, message: t('Please_input_the_description') }]} >
labelCol={{ span: 7 }} label={t('language')} name='language' className='w-1/2' rules={[{ required: true }]} >
{curTeamModal !== 'awel_layout' ? ( <>
Agents
) : ( )}
); }