mirror of
https://github.com/CherryHQ/cherry-studio.git
synced 2025-12-26 20:12:38 +08:00
fix(chat): handle agent and session state changes properly
update activeAgentId type to allow null and reset state when deleting agent add validation for missing agent/session in UI components
This commit is contained in:
parent
c52cc5a94f
commit
0be2177937
@ -1,9 +1,12 @@
|
||||
import { useAppDispatch } from '@renderer/store'
|
||||
import { setActiveAgentId, setActiveSessionIdAction } from '@renderer/store/runtime'
|
||||
import { AddAgentForm } from '@renderer/types'
|
||||
import { formatErrorMessageWithPrefix } from '@renderer/utils/error'
|
||||
import { useCallback } from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import useSWR from 'swr'
|
||||
|
||||
import { useRuntime } from '../useRuntime'
|
||||
import { useAgentClient } from './useAgentClient'
|
||||
|
||||
export const useAgents = () => {
|
||||
@ -16,6 +19,9 @@ export const useAgents = () => {
|
||||
return result.data
|
||||
}, [client])
|
||||
const { data, error, isLoading, mutate } = useSWR(key, fetcher)
|
||||
const { chat } = useRuntime()
|
||||
const { activeAgentId } = chat
|
||||
const dispatch = useAppDispatch()
|
||||
|
||||
const addAgent = useCallback(
|
||||
async (form: AddAgentForm) => {
|
||||
@ -34,6 +40,15 @@ export const useAgents = () => {
|
||||
async (id: string) => {
|
||||
try {
|
||||
await client.deleteAgent(id)
|
||||
dispatch(setActiveSessionIdAction({ agentId: id, sessionId: null }))
|
||||
if (activeAgentId === id) {
|
||||
const newId = data?.filter((a) => a.id !== id).find(() => true)?.id
|
||||
if (newId) {
|
||||
dispatch(setActiveAgentId(newId))
|
||||
} else {
|
||||
dispatch(setActiveAgentId(null))
|
||||
}
|
||||
}
|
||||
mutate((prev) => prev?.filter((a) => a.id !== id) ?? [])
|
||||
window.toast.success(t('common.delete_success'))
|
||||
} catch (error) {
|
||||
|
||||
@ -18,7 +18,7 @@ import { classNames } from '@renderer/utils'
|
||||
import { Flex } from 'antd'
|
||||
import { debounce } from 'lodash'
|
||||
import { AnimatePresence, motion } from 'motion/react'
|
||||
import React, { FC, useMemo, useState } from 'react'
|
||||
import React, { FC, useCallback, useMemo, useState } from 'react'
|
||||
import { useHotkeys } from 'react-hotkeys-hook'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import styled from 'styled-components'
|
||||
@ -172,6 +172,27 @@ const Chat: FC<Props> = (props) => {
|
||||
return () => <AgentSessionInputbar agentId={activeAgentId} sessionId={sessionId} />
|
||||
}, [activeAgentId, activeSessionId])
|
||||
|
||||
// TODO: more info
|
||||
const AgentInvalid = useCallback(() => {
|
||||
return (
|
||||
<div className="flex h-full w-full items-center justify-center">
|
||||
<div>
|
||||
<Alert color="warning" title="Select an agent" />
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}, [])
|
||||
|
||||
// TODO: more info
|
||||
const SessionInvalid = useCallback(() => {
|
||||
return (
|
||||
<div className="flex h-full w-full items-center justify-center">
|
||||
<div>
|
||||
<Alert color="warning" title="Create a session" />
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}, [])
|
||||
return (
|
||||
<Container id="chat" className={classNames([messageStyle, { 'multi-select-mode': isMultiSelectMode }])}>
|
||||
{isTopNavbar && (
|
||||
@ -213,7 +234,11 @@ const Chat: FC<Props> = (props) => {
|
||||
<Inputbar assistant={assistant} setActiveTopic={props.setActiveTopic} topic={props.activeTopic} />
|
||||
</>
|
||||
)}
|
||||
{activeTopicOrSession === 'session' && (
|
||||
{activeTopicOrSession === 'session' && !activeAgentId && <AgentInvalid />}
|
||||
{activeTopicOrSession === 'session' && activeAgentId && !activeSessionId[activeAgentId] && (
|
||||
<SessionInvalid />
|
||||
)}
|
||||
{activeTopicOrSession === 'session' && activeAgentId && activeSessionId[activeAgentId] && (
|
||||
<>
|
||||
<SessionMessages />
|
||||
<SessionInputBar />
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
import { Alert, cn, Spinner } from '@heroui/react'
|
||||
import { Alert, cn } from '@heroui/react'
|
||||
import { useRuntime } from '@renderer/hooks/useRuntime'
|
||||
import { useSettings } from '@renderer/hooks/useSettings'
|
||||
import { AnimatePresence, motion } from 'framer-motion'
|
||||
@ -24,6 +24,14 @@ const SessionsTab: FC<SessionsTabProps> = () => {
|
||||
)
|
||||
}
|
||||
|
||||
if (!activeAgentId) {
|
||||
return (
|
||||
<div>
|
||||
<Alert color="warning" title={'Select an agent'} />
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
<AnimatePresence mode="wait">
|
||||
<motion.div
|
||||
@ -35,26 +43,7 @@ const SessionsTab: FC<SessionsTabProps> = () => {
|
||||
'overflow-hidden',
|
||||
topicPosition === 'right' && navbarPosition === 'top' ? 'rounded-l-2xl border-t border-b border-l' : undefined
|
||||
)}>
|
||||
{!activeAgentId ? (
|
||||
<motion.div
|
||||
key="loading"
|
||||
initial={{ opacity: 0 }}
|
||||
animate={{ opacity: 1 }}
|
||||
exit={{ opacity: 0 }}
|
||||
transition={{ duration: 0.3 }}
|
||||
className="flex h-full flex-col items-center justify-center gap-3">
|
||||
<Spinner size="lg" color="primary" />
|
||||
<motion.p
|
||||
initial={{ opacity: 0, y: 5 }}
|
||||
animate={{ opacity: 1, y: 0 }}
|
||||
transition={{ delay: 0.2, duration: 0.3 }}
|
||||
className="text-foreground-500 text-sm">
|
||||
{t('common.loading')}...
|
||||
</motion.p>
|
||||
</motion.div>
|
||||
) : (
|
||||
<Sessions agentId={activeAgentId} />
|
||||
)}
|
||||
<Sessions agentId={activeAgentId} />
|
||||
</motion.div>
|
||||
</AnimatePresence>
|
||||
)
|
||||
|
||||
@ -158,7 +158,7 @@ const runtimeSlice = createSlice({
|
||||
// @ts-ignore ts2589 false positive
|
||||
state.chat.activeTopic = action.payload
|
||||
},
|
||||
setActiveAgentId: (state, action: PayloadAction<string>) => {
|
||||
setActiveAgentId: (state, action: PayloadAction<string | null>) => {
|
||||
state.chat.activeAgentId = action.payload
|
||||
},
|
||||
setActiveSessionIdAction: (state, action: PayloadAction<{ agentId: string; sessionId: string | null }>) => {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user