From 19fc20173b488b5695e60b58a351b924b595ac6d Mon Sep 17 00:00:00 2001 From: Abdul Rahman <81605929+abdulrahmancodes@users.noreply.github.com> Date: Mon, 1 Dec 2025 20:01:20 +0530 Subject: [PATCH] fix: lagging issue in ask AI during message streaming (#16201) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ## Changes ### 1. Fixed streaming lag with throttle parameter **Problem:** The AI chat was experiencing lag during message streaming because the messages array was being updated too frequently, causing all messages to re-render too quickly. **Solution:** Added the `experimental_throttle: 100` parameter to the `useChat` hook configuration. This throttles message updates during streaming to prevent excessive re-renders and improve performance. ### 2. Cleaned up useAgentChat hook return values **Context:** The `useAgentChat` hook primarily returns values from the underlying `useChat` hook, so there wasn't significant room for improvement regarding the "umbrella hook" pattern. However, some unnecessary values were being returned that weren't needed. **Solution:** - Removed `input` and `handleInputChange` from the `useAgentChat` hook return. These weren't needed since input state is already managed directly via Recoil state (`agentChatInputState`) in components. --- > [!NOTE] > Throttle message streaming updates and switch AI chat input management from context to Recoil; minor scroll behavior tweak. > > - **AI Chat performance**: > - Add `experimental_throttle: 100` to `useChat` in `useAgentChat` to reduce re-render frequency during streaming. > - **State management**: > - Migrate input handling to Recoil via `agentChatInputState`; remove `input` and `handleInputChange` from `AgentChatContext` and `useAgentChat` returns. > - Update `AIChatTab` and `SendMessageButton` to read/write input from Recoil and adjust hotkeys/disabled state accordingly. > - **UX behavior**: > - Remove smooth scroll behavior in `useAgentChatScrollToBottom`. > > Written by [Cursor Bugbot](https://cursor.com/dashboard?tab=bugbot) for commit 911b341ea1f7c63a4e1e27667da119d9a2960b78. This will update automatically on new commits. Configure [here](https://cursor.com/dashboard?tab=bugbot). --------- Co-authored-by: Félix Malfait --- .../src/modules/ai/components/AIChatTab.tsx | 11 ++++++++--- .../ai/components/internal/SendMessageButton.tsx | 11 +++++++---- .../src/modules/ai/contexts/AgentChatContext.ts | 3 --- .../twenty-front/src/modules/ai/hooks/useAgentChat.ts | 3 +-- .../modules/ai/hooks/useAgentChatScrollToBottom.ts | 1 - 5 files changed, 16 insertions(+), 13 deletions(-) diff --git a/packages/twenty-front/src/modules/ai/components/AIChatTab.tsx b/packages/twenty-front/src/modules/ai/components/AIChatTab.tsx index df76d907b1..c45a668cdd 100644 --- a/packages/twenty-front/src/modules/ai/components/AIChatTab.tsx +++ b/packages/twenty-front/src/modules/ai/components/AIChatTab.tsx @@ -19,10 +19,12 @@ import { AI_CHAT_INPUT_ID } from '@/ai/constants/AiChatInputId'; import { AI_CHAT_SCROLL_WRAPPER_ID } from '@/ai/constants/AiChatScrollWrapperId'; import { useAIChatFileUpload } from '@/ai/hooks/useAIChatFileUpload'; import { useAgentChatContextOrThrow } from '@/ai/hooks/useAgentChatContextOrThrow'; +import { agentChatInputState } from '@/ai/states/agentChatInputState'; import { contextStoreCurrentObjectMetadataItemIdComponentState } from '@/context-store/states/contextStoreCurrentObjectMetadataItemIdComponentState'; import { useRecoilComponentValue } from '@/ui/utilities/state/component-state/hooks/useRecoilComponentValue'; import { t } from '@lingui/core/macro'; import { useState } from 'react'; +import { useRecoilState } from 'recoil'; import { Button } from 'twenty-ui/input'; const StyledContainer = styled.div<{ isDraggingFile: boolean }>` @@ -63,9 +65,12 @@ const StyledButtonsContainer = styled.div` export const AIChatTab = () => { const [isDraggingFile, setIsDraggingFile] = useState(false); - const { isLoading, input, handleInputChange, messages, isStreaming, error } = + const { isLoading, messages, isStreaming, error } = useAgentChatContextOrThrow(); + const [agentChatInput, setAgentChatInput] = + useRecoilState(agentChatInputState); + const contextStoreCurrentObjectMetadataItemId = useRecoilComponentValue( contextStoreCurrentObjectMetadataItemIdComponentState, ); @@ -115,8 +120,8 @@ export const AIChatTab = () => {