Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
47 commits
Select commit Hold shift + click to select a range
38a296a
init
shaejaz May 21, 2026
8d1e0b4
fix types
shaejaz May 21, 2026
fd8f9dd
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz May 22, 2026
599683b
fix duplicate requests
shaejaz May 22, 2026
b867e28
rename current page suggestions
shaejaz May 26, 2026
aee97fd
add suggestions pills component
shaejaz May 26, 2026
01349ec
standalone suggestions
shaejaz May 26, 2026
b33b848
fix ssr
shaejaz May 26, 2026
6881fd8
remove ChatPageSummary widget (split to feat/chat-page-summary-widget)
shaejaz May 26, 2026
5479d0f
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz May 26, 2026
fe120b1
fix tests
shaejaz May 27, 2026
a9a6004
update api
shaejaz May 28, 2026
2e0f439
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz Jul 7, 2026
3b48a55
update endpoint, remove standalone naming
shaejaz Jul 9, 2026
71db731
add tests
shaejaz Jul 9, 2026
2fd7918
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz Jul 9, 2026
922aa54
chore(examples): revert example changes for chat-page-suggestions
shaejaz Jul 9, 2026
953baf4
add task name test
shaejaz Jul 9, 2026
aae135c
address comments
shaejaz Jul 9, 2026
5970f2b
fix bundlesize
shaejaz Jul 9, 2026
9f59a30
fix nextjs and loading states
shaejaz Jul 9, 2026
738eacb
address comments and fix test
shaejaz Jul 9, 2026
6bfbd52
add header
shaejaz Jul 9, 2026
30271bd
add streaming support
shaejaz Jul 12, 2026
82c47a1
rename widget
shaejaz Jul 12, 2026
ff9ce8a
move functionality to connector
shaejaz Jul 13, 2026
42fdb5b
add comments
shaejaz Jul 13, 2026
82241ca
add filters support
shaejaz Jul 13, 2026
0f37cfa
address comments
shaejaz Jul 14, 2026
1f6ab0f
update bundlesize
shaejaz Jul 14, 2026
b588873
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz Jul 14, 2026
1b0b390
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz Jul 16, 2026
f360a6f
address comments
shaejaz Jul 16, 2026
bd11185
Merge branch 'master' into feat/chat-page-suggestions-widget
shaejaz Jul 17, 2026
bf118b4
chore(chat): drop sessionStorage SSR guard (split to separate PR)
shaejaz Jul 17, 2026
88fdcc1
remove next and ssr changes
shaejaz Jul 17, 2026
99ae0b5
rename to prompt suggestions
shaejaz Jul 17, 2026
87c12b1
add back chat prompt suggestions
shaejaz Jul 17, 2026
9ee79ae
move back chat transport
shaejaz Jul 17, 2026
c52f220
rename connector
shaejaz Jul 17, 2026
ff78870
update bundlesize
shaejaz Jul 20, 2026
5781b1d
address comments
shaejaz Jul 20, 2026
3244084
update refer name
shaejaz Jul 20, 2026
f624a9e
use queryid
shaejaz Jul 21, 2026
8633901
address comments
shaejaz Jul 21, 2026
0aa15eb
update default task name
shaejaz Jul 21, 2026
8bd3025
update turn context
shaejaz Jul 21, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 7 additions & 7 deletions bundlesize.config.json
Original file line number Diff line number Diff line change
Expand Up @@ -10,19 +10,19 @@
},
{
"path": "./packages/instantsearch.js/dist/instantsearch.production.min.js",
"maxSize": "130.5 kB"
"maxSize": "133.5 kB"
},
{
"path": "./packages/instantsearch.js/dist/instantsearch.development.js",
"maxSize": "280 kB"
"maxSize": "282.5 kB"
},
{
"path": "packages/react-instantsearch-core/dist/umd/ReactInstantSearchCore.min.js",
"maxSize": "61.5 kB"
"maxSize": "63.75 kB"
},
{
"path": "packages/react-instantsearch/dist/umd/ReactInstantSearch.min.js",
"maxSize": "103.25 kB"
"maxSize": "106.25 kB"
},
{
"path": "packages/vue-instantsearch/vue2/umd/index.js",
Expand All @@ -46,7 +46,7 @@
},
{
"path": "./packages/instantsearch.css/themes/algolia-min.css",
"maxSize": "10 kB"
"maxSize": "10.25 kB"
},
{
"path": "./packages/instantsearch.css/themes/reset.css",
Expand All @@ -66,7 +66,7 @@
},
{
"path": "./packages/instantsearch.css/themes/satellite.css",
"maxSize": "11.75 kB"
"maxSize": "12 kB"
},
{
"path": "./packages/instantsearch.css/themes/satellite-min.css",
Expand All @@ -78,7 +78,7 @@
},
{
"path": "./packages/instantsearch.css/components/chat-min.css",
"maxSize": "5.75 kB"
"maxSize": "6 kB"
},
{
"path": "./packages/instantsearch.css/components/autocomplete.css",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,184 @@
/**
* @jest-environment @instantsearch/testutils/jest-environment-jsdom.ts
*/
/** @jsx createElement */
import { render } from '@testing-library/preact';
import { Fragment, createElement } from 'preact';

import { createPromptSuggestionsComponent } from '../chat/PromptSuggestions';

describe('PromptSuggestions', () => {
const PromptSuggestions = createPromptSuggestionsComponent({
createElement,
Fragment,
});

test('renders an empty root when there are no suggestions and not loading', () => {
const { container } = render(
<PromptSuggestions suggestions={[]} onSuggestionClick={jest.fn()} />
);

const root = container.querySelector('.ais-PromptSuggestions');
expect(root).toBeInTheDocument();
expect(root).toBeEmptyDOMElement();
expect(
container.querySelector('.ais-PromptSuggestions-skeleton')
).not.toBeInTheDocument();
});

test('forwards HTML attributes and merges className onto the root', () => {
const { container } = render(
<PromptSuggestions
suggestions={[]}
onSuggestionClick={jest.fn()}
className="CUSTOM"
title="hello"
/>
);

const root = container.querySelector<HTMLDivElement>(
'.ais-PromptSuggestions'
)!;
expect(root.classList.contains('CUSTOM')).toBe(true);
expect(root.title).toBe('hello');
});

test('renders the default header when there are suggestions', () => {
const { container } = render(
<PromptSuggestions
suggestions={['A', 'B']}
onSuggestionClick={jest.fn()}
/>
);

const header = container.querySelector('.ais-PromptSuggestions-header');
expect(header).toBeInTheDocument();
expect(
container.querySelector('.ais-PromptSuggestions-headerTitle')
).toHaveTextContent('Suggestions');
});

test('translates the header title', () => {
const { container } = render(
<PromptSuggestions
suggestions={['A']}
translations={{ headerTitle: 'Ideas' }}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelector('.ais-PromptSuggestions-headerTitle')
).toHaveTextContent('Ideas');
});

test('renders the default header while loading', () => {
const { container } = render(
<PromptSuggestions
suggestions={[]}
isLoading={true}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelector('.ais-PromptSuggestions-header')
).toBeInTheDocument();
});

test('does not render the header when empty and not loading', () => {
const { container } = render(
<PromptSuggestions suggestions={[]} onSuggestionClick={jest.fn()} />
);

expect(
container.querySelector('.ais-PromptSuggestions-header')
).not.toBeInTheDocument();
});

test('disables the header when headerComponent is false', () => {
const { container } = render(
<PromptSuggestions
suggestions={['A']}
headerComponent={false}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelector('.ais-PromptSuggestions-header')
).not.toBeInTheDocument();
expect(
container.querySelectorAll('.ais-PromptSuggestions-suggestion')
).toHaveLength(1);
});

test('renders a custom header component', () => {
const { container } = render(
<PromptSuggestions
suggestions={['A']}
headerComponent={() => <div className="custom-header">Custom</div>}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelector('.ais-PromptSuggestions-header')
).not.toBeInTheDocument();
const custom = container.querySelector('.custom-header');
expect(custom).toBeInTheDocument();
expect(custom).toHaveTextContent('Custom');
});

test('renders the suggestion pills', () => {
const { container } = render(
<PromptSuggestions
suggestions={['A', 'B']}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelectorAll('.ais-PromptSuggestions-suggestion')
).toHaveLength(2);
expect(
container.querySelector('.ais-PromptSuggestions-skeleton')
).not.toBeInTheDocument();
});

test('renders skeletons while loading with no suggestions yet', () => {
const { container } = render(
<PromptSuggestions
suggestions={[]}
isLoading={true}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelector('.ais-PromptSuggestions-skeleton')
).toBeInTheDocument();
expect(
container.querySelectorAll('.ais-PromptSuggestions-skeletonItem')
).toHaveLength(3);
});

test('keeps existing pills (no skeletons) while refetching', () => {
// Loading with suggestions already present must not swap the pills for
// skeletons — that would make existing suggestions disappear mid-refetch.
const { container } = render(
<PromptSuggestions
suggestions={['A', 'B']}
isLoading={true}
onSuggestionClick={jest.fn()}
/>
);

expect(
container.querySelectorAll('.ais-PromptSuggestions-suggestion')
).toHaveLength(2);
expect(
container.querySelector('.ais-PromptSuggestions-skeleton')
).not.toBeInTheDocument();
});
});
Loading
Loading