From 3be2c8e1606ccbb7ce21ee83968db2ba4239eafe Mon Sep 17 00:00:00 2001 From: "Ian Christopher B. de Jesus" <3683356+iandjx@users.noreply.github.com> Date: Thu, 20 Mar 2025 21:49:43 +0800 Subject: [PATCH] Refactor ChatAppForm2 component and clean up imports in related files. Remove unused states and components from Apps page, and update edit page to use ChatAppForm2. Enhance navigation with back button in edit view. --- webapp/src/components/ChatAppForm2.tsx | 87 +++--------- .../pages/[resourceSlug]/app/[appId]/edit.tsx | 24 +++- webapp/src/pages/[resourceSlug]/apps.tsx | 134 +----------------- 3 files changed, 42 insertions(+), 203 deletions(-) diff --git a/webapp/src/components/ChatAppForm2.tsx b/webapp/src/components/ChatAppForm2.tsx index 1bd70ce35..682224588 100644 --- a/webapp/src/components/ChatAppForm2.tsx +++ b/webapp/src/components/ChatAppForm2.tsx @@ -1,61 +1,26 @@ import * as API from '@api'; - import { AgentCreatedDisplay } from 'components/apps/AgentCreatedDisplay'; import { AgentSelectDisplay } from 'components/apps/AgentSelectDisplay'; import { CreateAgentSheet } from 'components/apps/CreateAgentSheet'; import { InsightChat } from 'components/apps/InsightChat'; -import Spinner from 'components/Spinner'; -import { useAccountContext } from 'context/account'; -import { useStepContext } from 'context/stepwrapper'; -import { useThemeContext } from 'context/themecontext'; import { AgentsDataReturnType } from 'controllers/agent'; -import { AppsDataReturnType } from 'controllers/app'; import { Model } from 'db/model'; -import useAutocompleteDropdown from 'hooks/useAutoCompleteDropdown'; -import { ChevronDown, Circle, Layout, Pencil, SendHorizonal, Trash2 } from 'lucide-react'; -import { MultiSelect } from 'modules/components/multi-select'; +import { Circle, Pencil, SendHorizonal, Trash2 } from 'lucide-react'; import { Button } from 'modules/components/ui/button'; -import { - DropdownMenu, - DropdownMenuContent, - DropdownMenuItem, - DropdownMenuTrigger -} from 'modules/components/ui/dropdown-menu'; import { useRouter } from 'next/router'; -// import agents from 'pages/[resourceSlug]/agents'; + import { usePostHog } from 'posthog-js/react'; import { useEffect, useState } from 'react'; import { toast } from 'react-toastify'; -import { useAgentStore } from 'store/agent'; import { Agent } from 'struct/agent'; import { App, AppType } from 'struct/app'; -import { ChatAppAllowedModels } from 'struct/model'; -import { SharingMode } from 'struct/sharing'; -import { ToolType } from 'struct/tool'; import AddEmailModal from './AddEmailModal'; import ConfirmModal from './ConfirmModal'; -import CreateDatasourceModal from './CreateDatasourceModal'; -import CreateModelModal from './CreateModelModal'; -import CreateToolModal from './modal/CreateToolModal'; import SharingModeSelect from './SharingModeSelect'; -import CreateVariableModal from './variables/CreateVariableModal'; - -const chatAppTaglines = [ - 'Build single agent chat bots (like GPTS)', - 'Integrate RAG datasources', - 'Add custom agent', - 'Integrate custom tools', - 'Embed your chat app via IFrame' -]; - -const processAppTaglines = [ - 'Build Multi-Agent Process Apps (powered by Crew AI)', - 'Integrate RAG datasources', - 'Add custom code tools', - 'Add tasks', - 'Embed your process app via IFrame' -]; +import { SharingMode } from 'struct/sharing'; +import { useAccountContext } from 'context/account'; +import Link from 'next/link'; export default function Apps({ app, @@ -126,6 +91,8 @@ export default function Apps({ const router = useRouter(); const { resourceSlug } = router.query; + // const { step, setStep } = useStepContext(); + const [sharingMode, setSharingMode] = useState(app?.sharingConfig?.mode || SharingMode.TEAM); const [shareLinkShareId, setShareLinkShareId] = useState(editing ? app?.shareLinkShareId : null); const [appName, setAppName] = useState(app?.name || 'Untitled Chat App'); @@ -342,7 +309,9 @@ export default function Apps({ return (
-

Apps

+ +

Apps

+ >

Create App

> @@ -355,8 +324,7 @@ export default function Apps({
+ onSubmit={appPost}>
@@ -388,8 +356,7 @@ export default function Apps({ setAppName(''); } }} - className='hover:text-[#4F46E5] transition-colors' - > + className='hover:text-[#4F46E5] transition-colors'>
@@ -465,8 +432,7 @@ export default function Apps({
setEditingStarterId(starter.id)} - > + onClick={() => setEditingStarterId(starter.id)}> {editingStarterId === starter.id ? ( + onClick={handleAddStarter}> + Add

- {/*
-

Display Settings

- - - - - - Dropdown Item - - -
*/} + onClick={() => (editing ? callback?.() : router.back())} + className='bg-transparent text-foreground hover:bg-transparent hover:text-foreground p-0 border-0 shadow-none outline-none'> Cancel
diff --git a/webapp/src/pages/[resourceSlug]/app/[appId]/edit.tsx b/webapp/src/pages/[resourceSlug]/app/[appId]/edit.tsx index 1d6c4035f..b723c72ad 100644 --- a/webapp/src/pages/[resourceSlug]/app/[appId]/edit.tsx +++ b/webapp/src/pages/[resourceSlug]/app/[appId]/edit.tsx @@ -1,6 +1,6 @@ import * as API from '@api'; import { ChevronLeftIcon, PhotoIcon, UserCircleIcon } from '@heroicons/react/24/solid'; -import ChatAppForm from 'components/ChatAppForm'; +import ChatAppForm2 from 'components/ChatAppForm2'; import CrewAppForm from 'components/CrewAppForm'; import Spinner from 'components/Spinner'; import { useAccountContext } from 'context/account'; @@ -9,6 +9,7 @@ import Link from 'next/link'; import { useRouter } from 'next/router'; import React, { useEffect, useState } from 'react'; import { AppType } from 'struct/app'; +import { Button } from 'modules/components/ui/button'; export default function EditApp(props) { const [accountContext]: any = useAccountContext(); @@ -35,6 +36,10 @@ export default function EditApp(props) { fetchAppFormData(); }, [resourceSlug]); + const handleBack = () => { + router.push(`/${resourceSlug}/apps`); + }; + if (app == null) { return ; } @@ -45,12 +50,17 @@ export default function EditApp(props) { {`Edit App - ${teamName}`} -
-

Edit App - {app.name}

+
+
+ +

Edit App - {app.name}

+
{(app.type as AppType) === AppType.CHAT ? ( - { + router.push(`/${resourceSlug}/apps`); + }} /> ) : ( { + router.push(`/${resourceSlug}/apps`); + }} /> )} diff --git a/webapp/src/pages/[resourceSlug]/apps.tsx b/webapp/src/pages/[resourceSlug]/apps.tsx index 1cd66e560..5c6ead26e 100644 --- a/webapp/src/pages/[resourceSlug]/apps.tsx +++ b/webapp/src/pages/[resourceSlug]/apps.tsx @@ -42,8 +42,6 @@ import { SharingMode } from 'struct/sharing'; import { toast } from 'react-toastify'; import ChatAppForm2 from 'components/ChatAppForm2'; import { Sheet, SheetContent, SheetHeader, SheetTitle } from 'modules/components/ui/sheet'; -import { Model } from 'db/model'; -import { Agent } from 'struct/agent'; const DeleteDialog = ({ openDeleteDialog, @@ -100,83 +98,6 @@ const DeleteDialog = ({ ); }; -const EditAppSheet = ({ - open, - setOpen, - selectedApp, - onAppUpdate, - toolChoices, - modelChoices, - agentChoices, - fetchFormData // Add this prop -}: { - open: boolean; - setOpen: (open: boolean) => void; - selectedApp: App; - onAppUpdate: () => void; - toolChoices: any[]; - modelChoices: any[]; - agentChoices: any[]; - fetchFormData: () => Promise; // Add this type -}) => { - // Add default values for missing properties - const enrichedApp = { - ...selectedApp, - chatAppConfig: { - ...selectedApp?.chatAppConfig, - maxMessages: selectedApp?.chatAppConfig?.maxMessages || 30 - }, - sharingConfig: { - ...selectedApp?.sharingConfig, - mode: selectedApp?.sharingConfig?.mode || SharingMode.TEAM, - permissions: selectedApp?.sharingConfig?.permissions || {} - }, - conversationStarters: ['Help me brainstorm some ideas', 'What can you help me with?'], - description: selectedApp?.description || '', - name: selectedApp?.name || 'Untitled Chat App', - type: selectedApp?.type || AppType.CHAT - }; - - return ( - { - if (!open) { - // Force a slight delay before resetting pointer events - setTimeout(() => { - document.body.style.pointerEvents = 'auto'; - document.body.style.cursor = 'auto'; - }, 100); - } - setOpen(open); - }}> - - - Edit App - -
- { - setOpen(false); - onAppUpdate(); - }} - toolChoices={toolChoices} // Pass these from parent if available - modelChoices={modelChoices} // Pass these from parent if available - agentChoices={agentChoices} // Pass these from parent if available - whiteListSharingChoices={Object.values(enrichedApp.sharingConfig.permissions || {})} - /> -
-
-
- ); -}; - export default function Apps(props) { const { agents } = useAgentStore(); const [openDeleteDialog, setOpenDeleteDialog] = useState(false); @@ -194,44 +115,9 @@ export default function Apps(props) { const { apps } = state; const [selectedAgentId, setSelectedAgentId] = useState(null); - const [selectedApp, setSelectedApp] = useState(null); const appsToDisplay = filteredApps.length > 0 ? filteredApps : apps; - // Add these states to fetch required data - const [toolChoices, setToolChoices] = useState([]); - const [modelChoices, setModelChoices] = useState([]); - const [agentChoices, setAgentChoices] = useState([]); - - // Add function to fetch all required data - const fetchFormData = async () => { - try { - // Add your API calls here to fetch tools, models, and agents - const [toolsRes, modelsRes, agentsRes] = await Promise.all([ - API.getTools({ resourceSlug, _csrf: csrf }, dispatch, setError, router), - API.getModels({ resourceSlug, _csrf: csrf }, dispatch, setError, router), - API.getAgents({ resourceSlug, _csrf: csrf }, dispatch, setError, router) - ]); - - // Ensure we're setting arrays even if the response is null/undefined - setToolChoices(toolsRes?.data || []); - setModelChoices(modelsRes?.data || []); - setAgentChoices(agentsRes?.data || []); - } catch (error) { - console.error('Error fetching form data:', error); - toast.error('Error loading data'); - // Set empty arrays on error to prevent undefined errors - setToolChoices([]); - setModelChoices([]); - setAgentChoices([]); - } - }; - - // Add useEffect to fetch data on mount - useEffect(() => { - fetchFormData(); - }, [resourceSlug]); - async function startSession(appId: ObjectId) { await API.addSession( { @@ -293,12 +179,8 @@ export default function Apps(props) { }, []); // Add handler for opening edit sheet - const handleOpenEditSheet = (app: App) => { - setSelectedApp(app); - setOpenEditSheet(true); - // Ensure body pointer events are reset when opening - document.body.style.pointerEvents = 'auto'; - document.body.style.cursor = 'auto'; + const handleEditApp = (app: App) => { + router.push(`/${resourceSlug}/app/${app._id}/edit`); }; if (!apps) { @@ -312,16 +194,6 @@ export default function Apps(props) { setOpenDeleteDialog={setOpenDeleteDialog} onDelete={() => deleteApp(selectedAgentId)} /> -

Apps

@@ -377,7 +249,7 @@ export default function Apps(props) { - handleOpenEditSheet(app)}> + handleEditApp(app)}> Edit