fix(askai): Preserve conversation when transitioning to Ask AI
This commit is contained in:
parent
e9f932b7ab
commit
81ea2c3436
4 changed files with 81 additions and 1 deletions
5
.changeset/sparkly-kings-wink.md
Normal file
5
.changeset/sparkly-kings-wink.md
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
---
|
||||
"@docsearch/react": patch
|
||||
---
|
||||
|
||||
fix(askai): preserve the conversation when opening Ask AI from the results row [#3010](https://github.com/algolia/docsearch/issues/3010)
|
||||
|
|
@ -487,14 +487,20 @@ export function DocSearchAskAiModal({
|
|||
useRefreshOnInitialQuery({ initialQuery, inputRef, refresh });
|
||||
|
||||
const hasCurrentMessages = messages.length > 0;
|
||||
const previousIsAskAiActive = React.useRef(isAskAiActive);
|
||||
|
||||
// Refresh the autocomplete results when ask ai is toggled off
|
||||
// helps return to the previous ac state and start screen
|
||||
React.useEffect(() => {
|
||||
const wasAskAiActive = previousIsAskAiActive.current;
|
||||
previousIsAskAiActive.current = isAskAiActive;
|
||||
|
||||
if (!isAskAiActive) {
|
||||
autocomplete.refresh();
|
||||
|
||||
if (hasCurrentMessages) {
|
||||
// Reset only after leaving Ask AI, not when its first message arrives
|
||||
// before the parent toggle update commits.
|
||||
if (wasAskAiActive && hasCurrentMessages) {
|
||||
startNewConversation();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,68 @@
|
|||
import { render } from '@testing-library/react';
|
||||
import type { UIMessage } from 'ai';
|
||||
import React from 'react';
|
||||
import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest';
|
||||
|
||||
import { DocSearchAskAiModal } from '../DocSearchAskAiModal';
|
||||
|
||||
const mocks = vi.hoisted(() => ({
|
||||
startNewConversation: vi.fn(),
|
||||
useAskAi: vi.fn(),
|
||||
}));
|
||||
|
||||
vi.mock('../useAskAi', () => ({
|
||||
useAskAi: mocks.useAskAi,
|
||||
}));
|
||||
|
||||
describe('DocSearchAskAiModal', () => {
|
||||
let messages: UIMessage[] = [];
|
||||
|
||||
beforeEach(() => {
|
||||
messages = [];
|
||||
mocks.startNewConversation.mockReset();
|
||||
mocks.useAskAi.mockImplementation(() => ({
|
||||
askAiError: undefined,
|
||||
chatId: 'chat-id',
|
||||
conversations: { add: vi.fn(), getAll: () => [] },
|
||||
exchanges: [],
|
||||
isStreaming: false,
|
||||
messages,
|
||||
restoreConversation: vi.fn(),
|
||||
sendFeedback: vi.fn(),
|
||||
sendMessage: vi.fn(),
|
||||
setMessages: vi.fn(),
|
||||
startNewConversation: mocks.startNewConversation,
|
||||
status: 'ready',
|
||||
stopAskAiStreaming: vi.fn(),
|
||||
}));
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
vi.clearAllMocks();
|
||||
});
|
||||
|
||||
it('does not reset a conversation when its first message arrives before Ask AI activates', () => {
|
||||
const props = {
|
||||
apiKey: 'api-key',
|
||||
appId: 'app-id',
|
||||
askAi: 'agent-id',
|
||||
indices: ['index-name'],
|
||||
initialScrollY: 0,
|
||||
onAskAiToggle: vi.fn(),
|
||||
};
|
||||
const { rerender } = render(
|
||||
<DocSearchAskAiModal {...props} isAskAiActive={false} />
|
||||
);
|
||||
|
||||
messages = [
|
||||
{
|
||||
id: 'message-id',
|
||||
parts: [{ text: 'Question', type: 'text' }],
|
||||
role: 'user',
|
||||
},
|
||||
];
|
||||
rerender(<DocSearchAskAiModal {...props} isAskAiActive={false} />);
|
||||
|
||||
expect(mocks.startNewConversation).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
|
@ -500,6 +500,7 @@ describe('api', () => {
|
|||
expect(
|
||||
document.querySelector('.DocSearch-AskAiScreen')
|
||||
).toBeInTheDocument();
|
||||
expect(await screen.findByText('hello')).toBeInTheDocument();
|
||||
|
||||
// could be "Answering..." or "Ask another question..."
|
||||
// where "Ask another question..." is actually an input's placeholder text
|
||||
|
|
|
|||
Loading…
Reference in a new issue