@brainfish-ai/components 0.16.10-alpha.4 → 0.16.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (31) hide show
  1. package/dist/button-group.d.ts +21 -0
  2. package/dist/chat-search.d.ts +1 -0
  3. package/dist/componentns/ui/button-group.d.ts +2 -0
  4. package/dist/components/ui/spinner.d.ts +3 -0
  5. package/dist/esm/chunks/{ChatSearch.BV8FTS2Y.js → ChatSearch.B4QTqo-0.js} +185 -14
  6. package/dist/esm/chunks/ChatSearch.B4QTqo-0.js.map +1 -0
  7. package/dist/esm/chunks/{index.tOGWkez1.js → index.BqibIWDw.js} +17 -3
  8. package/dist/esm/chunks/index.BqibIWDw.js.map +1 -0
  9. package/dist/esm/componentns/ui/button-group.js +74 -0
  10. package/dist/esm/componentns/ui/button-group.js.map +1 -0
  11. package/dist/esm/components/chat-search.js +1 -1
  12. package/dist/esm/components/ui/button.js +4 -4
  13. package/dist/esm/components/ui/button.js.map +1 -1
  14. package/dist/esm/components/ui/div-button.js +1 -1
  15. package/dist/esm/components/ui/item.js +3 -3
  16. package/dist/esm/components/ui/item.js.map +1 -1
  17. package/dist/esm/components/ui/select.js +1 -1
  18. package/dist/esm/components/ui/select.js.map +1 -1
  19. package/dist/esm/components/ui/spinner.js +18 -0
  20. package/dist/esm/components/ui/spinner.js.map +1 -0
  21. package/dist/esm/components/ui/textarea.js +1 -1
  22. package/dist/esm/components/ui/textarea.js.map +1 -1
  23. package/dist/esm/index.css +1 -1
  24. package/dist/esm/index.js +1 -1
  25. package/dist/index.d.ts +1 -0
  26. package/dist/spinner.d.ts +5 -0
  27. package/dist/stats.html +1 -1
  28. package/package.json +2 -2
  29. package/tailwind.config.js +1 -0
  30. package/dist/esm/chunks/ChatSearch.BV8FTS2Y.js.map +0 -1
  31. package/dist/esm/chunks/index.tOGWkez1.js.map +0 -1
@@ -0,0 +1,21 @@
1
+ import { ClassProp } from 'class-variance-authority/types';
2
+ import { default as default_2 } from 'react';
3
+ import * as React_2 from 'react';
4
+ import * as SeparatorPrimitive from '@radix-ui/react-separator';
5
+ import { VariantProps } from 'class-variance-authority';
6
+
7
+ export declare function ButtonGroup({ className, orientation, ...props }: default_2.ComponentProps<"div"> & VariantProps<typeof buttonGroupVariants>): default_2.JSX.Element;
8
+
9
+ export declare function ButtonGroupSeparator({ className, orientation, ...props }: default_2.ComponentProps<typeof Separator>): default_2.JSX.Element;
10
+
11
+ export declare function ButtonGroupText({ className, asChild, ...props }: default_2.ComponentProps<"div"> & {
12
+ asChild?: boolean;
13
+ }): default_2.JSX.Element;
14
+
15
+ export declare const buttonGroupVariants: (props?: ({
16
+ orientation?: "horizontal" | "vertical" | null | undefined;
17
+ } & ClassProp) | undefined) => string;
18
+
19
+ declare const Separator: React_2.ForwardRefExoticComponent<Omit<SeparatorPrimitive.SeparatorProps & React_2.RefAttributes<HTMLDivElement>, "ref"> & React_2.RefAttributes<HTMLDivElement>>;
20
+
21
+ export { }
@@ -231,6 +231,7 @@ export declare interface ChatSearchProps {
231
231
  secretAttributes?: string;
232
232
  allowedRegions?: string[];
233
233
  style?: React.CSSProperties;
234
+ isAgentAssist?: boolean;
234
235
  isSearchWidget?: boolean;
235
236
  }
236
237
 
@@ -0,0 +1,2 @@
1
+ export * from '../../components/ui/button-group'
2
+ export {}
@@ -0,0 +1,3 @@
1
+ import { default as React } from 'react';
2
+ declare function Spinner({ className, ...props }: React.ComponentProps<"svg">): React.JSX.Element;
3
+ export { Spinner };
@@ -24,6 +24,7 @@ import { Collapsible, CollapsibleTrigger, CollapsibleContent } from '../componen
24
24
  import { F as Feedback } from './feedback.NWn6_mYe.js';
25
25
  import { G as GeneratingStar } from './generating-star.COkD0gHd.js';
26
26
  import { getCountry } from 'countries-and-timezones';
27
+ import { Switch } from '../components/ui/switch.js';
27
28
  import { C as Combobox } from './combobox.CkN-wAHB.js';
28
29
  import { T as TwoLevelCombobox } from './two-level-combobox.DsWPDcI6.js';
29
30
  import { ScrollArea } from '../components/ui/scroll-area.js';
@@ -4501,6 +4502,135 @@ const useSubscriptionManager = () => {
4501
4502
  return { subscribeToStateChanges };
4502
4503
  };
4503
4504
 
4505
+ const useIncludePage = ({ isAgentAssist, apiKey, trackEvent }) => {
4506
+ const [includePageEnabled, setIncludePageEnabled] = useState(false);
4507
+ const [includePageLoading, setIncludePageLoading] = useState(false);
4508
+ const [includePageDisabled, setIncludePageDisabled] = useState(false);
4509
+ const sendMessageToParent = useCallback(
4510
+ (message, timeout = 5e3) => {
4511
+ return new Promise((resolve, reject) => {
4512
+ const requestId = createConversationId();
4513
+ let timeoutId;
4514
+ const handler = (event) => {
4515
+ if (event.data.requestId === requestId) {
4516
+ clearTimeout(timeoutId);
4517
+ window.removeEventListener("message", handler);
4518
+ resolve(event.data);
4519
+ }
4520
+ };
4521
+ timeoutId = setTimeout(() => {
4522
+ window.removeEventListener("message", handler);
4523
+ reject(new Error("Request timeout"));
4524
+ }, timeout);
4525
+ window.addEventListener("message", handler);
4526
+ window.parent.postMessage({ ...message, requestId, widgetKey: apiKey }, "*");
4527
+ });
4528
+ },
4529
+ [apiKey]
4530
+ );
4531
+ const handleIncludePageToggle = useCallback(
4532
+ async (enabled) => {
4533
+ setIncludePageLoading(true);
4534
+ try {
4535
+ if (enabled) {
4536
+ const response = await sendMessageToParent({
4537
+ type: "REQUEST_PAGE_PERMISSION"
4538
+ });
4539
+ if (!response.granted) {
4540
+ trackEvent?.("Include Page Permission Denied", {});
4541
+ throw new Error("Permission denied");
4542
+ }
4543
+ window.parent.postMessage(
4544
+ {
4545
+ type: "UPDATE_PAGE_TOGGLE_STATE",
4546
+ enabled: true,
4547
+ widgetKey: apiKey
4548
+ },
4549
+ "*"
4550
+ );
4551
+ trackEvent?.("Include Page Enabled", {});
4552
+ setIncludePageEnabled(true);
4553
+ } else {
4554
+ window.parent.postMessage(
4555
+ {
4556
+ type: "UPDATE_PAGE_TOGGLE_STATE",
4557
+ enabled: false,
4558
+ widgetKey: apiKey
4559
+ },
4560
+ "*"
4561
+ );
4562
+ trackEvent?.("Include Page Disabled", {});
4563
+ setIncludePageEnabled(false);
4564
+ }
4565
+ } catch (error) {
4566
+ console.error("Failed to toggle include page:", error);
4567
+ setIncludePageEnabled(false);
4568
+ } finally {
4569
+ setIncludePageLoading(false);
4570
+ }
4571
+ },
4572
+ [apiKey, sendMessageToParent, trackEvent]
4573
+ );
4574
+ const fetchPageContext = useCallback(
4575
+ async (conversationId, searchQuery) => {
4576
+ if (!includePageEnabled || !isAgentAssist || includePageDisabled) {
4577
+ return void 0;
4578
+ }
4579
+ try {
4580
+ setIncludePageLoading(true);
4581
+ const response = await sendMessageToParent(
4582
+ {
4583
+ type: "REQUEST_PAGE_CONTENT"
4584
+ },
4585
+ 5e3
4586
+ );
4587
+ if (response.success && response.content) {
4588
+ trackEvent?.("Page Content Included", {
4589
+ conversationId,
4590
+ searchQuery,
4591
+ contentLength: response.content.length
4592
+ });
4593
+ return [
4594
+ {
4595
+ type: "text",
4596
+ text: `I am currently viewing this web page:
4597
+
4598
+ ${response.content}`
4599
+ }
4600
+ ];
4601
+ }
4602
+ return void 0;
4603
+ } catch (error) {
4604
+ console.error("Failed to fetch page content:", error);
4605
+ trackEvent?.("Page Content Fetch Failed", { conversationId, searchQuery });
4606
+ return void 0;
4607
+ } finally {
4608
+ setIncludePageLoading(false);
4609
+ }
4610
+ },
4611
+ [includePageEnabled, isAgentAssist, includePageDisabled, sendMessageToParent, trackEvent]
4612
+ );
4613
+ useEffect(() => {
4614
+ if (!isAgentAssist) return;
4615
+ const handleMessage = (event) => {
4616
+ const data = event.data;
4617
+ if (data.type === "INCLUDE_PAGE_STATE") {
4618
+ setIncludePageEnabled(data.enabled || false);
4619
+ setIncludePageDisabled(data.disabled || false);
4620
+ }
4621
+ };
4622
+ window.addEventListener("message", handleMessage);
4623
+ return () => window.removeEventListener("message", handleMessage);
4624
+ }, [isAgentAssist]);
4625
+ return {
4626
+ includePageEnabled,
4627
+ includePageLoading,
4628
+ includePageDisabled,
4629
+ handleIncludePageToggle,
4630
+ fetchPageContext
4631
+ };
4632
+ };
4633
+
4504
4634
  function Answer({
4505
4635
  index,
4506
4636
  blocks = [],
@@ -4763,6 +4893,27 @@ function ScrollToBottomArrow({ onClick }) {
4763
4893
  );
4764
4894
  }
4765
4895
 
4896
+ function IncludePageToggle({ value, loading, disabled, onToggle }) {
4897
+ return /* @__PURE__ */ React__default.createElement("div", { className: "flex items-center gap-2" }, /* @__PURE__ */ React__default.createElement(Switch, { id: "include-page", checked: value, onCheckedChange: onToggle, disabled: loading || disabled }), /* @__PURE__ */ React__default.createElement("label", { htmlFor: "include-page", className: "text-sm text-foreground flex items-center gap-2" }, "Include page", loading && /* @__PURE__ */ React__default.createElement("div", { className: "animate-spin rounded-full size-3 border-2 border-t-transparent border-primary" })));
4898
+ }
4899
+
4900
+ const FeatureFlagContext = createContext(void 0);
4901
+ function FeatureFlagProvider({ children, flags }) {
4902
+ return /* @__PURE__ */ React__default.createElement(FeatureFlagContext.Provider, { value: flags ?? {} }, children);
4903
+ }
4904
+ function useBooleanFlagValue(flagKey, defaultValue) {
4905
+ const flags = useContext(FeatureFlagContext);
4906
+ if (!flags) {
4907
+ console.warn(`useBooleanFlagValue("${flagKey}") used outside of FeatureFlagProvider. Returning default value.`);
4908
+ return defaultValue;
4909
+ }
4910
+ const value = flags[flagKey];
4911
+ if (value === void 0) {
4912
+ return defaultValue;
4913
+ }
4914
+ return Boolean(value);
4915
+ }
4916
+
4766
4917
  const PrimarySearch = React__default.forwardRef(
4767
4918
  ({
4768
4919
  query,
@@ -4782,10 +4933,16 @@ const PrimarySearch = React__default.forwardRef(
4782
4933
  onRemoveImage,
4783
4934
  isSearching = false,
4784
4935
  autocompleteSuggestions = [],
4785
- onAutocompleteSuggestionSelect
4936
+ onAutocompleteSuggestionSelect,
4937
+ isAgentAssist = false,
4938
+ includePageEnabled = false,
4939
+ includePageLoading = false,
4940
+ includePageDisabled = false,
4941
+ onIncludePageToggle
4786
4942
  }, ref) => {
4787
4943
  const fileInputRef = useRef(null);
4788
4944
  const [showSuggestions, setShowSuggestions] = useState(false);
4945
+ const showIncludePageToggle = useBooleanFlagValue("showIncludePageToggle", false);
4789
4946
  const regionItems = [
4790
4947
  {
4791
4948
  value: "all",
@@ -4956,7 +5113,7 @@ const PrimarySearch = React__default.forwardRef(
4956
5113
  },
4957
5114
  /* @__PURE__ */ React__default.createElement(X, { className: "size-3 text-white", "aria-label": "Remove image" })
4958
5115
  )))),
4959
- !shouldShowSuggestions && /* @__PURE__ */ React__default.createElement("div", { className: "flex items-center justify-between px-3 py-2 border-t border-border" }, /* @__PURE__ */ React__default.createElement("div", { className: "flex gap-1", "data-name": "collections-dropdown" }, allowedRegions.length > 0 && collections.length > 0 ? (
5116
+ !shouldShowSuggestions && /* @__PURE__ */ React__default.createElement("div", { className: "flex items-center justify-between px-3 py-2 border-t border-border" }, /* @__PURE__ */ React__default.createElement("div", { className: "flex gap-2" }, /* @__PURE__ */ React__default.createElement("div", { className: "flex gap-1", "data-name": "collections-dropdown" }, allowedRegions.length > 0 && collections.length > 0 ? (
4960
5117
  // Two-level selection: Region -> Collection
4961
5118
  /* @__PURE__ */ React__default.createElement(
4962
5119
  TwoLevelCombobox,
@@ -4989,7 +5146,15 @@ const PrimarySearch = React__default.forwardRef(
4989
5146
  onChange: (value) => onCollectionChange?.(value)
4990
5147
  }
4991
5148
  )
4992
- ) : null, !disableImageAttachment && /* @__PURE__ */ React__default.createElement(React__default.Fragment, null, /* @__PURE__ */ React__default.createElement(
5149
+ ) : null), isAgentAssist && onIncludePageToggle && showIncludePageToggle && /* @__PURE__ */ React__default.createElement(
5150
+ IncludePageToggle,
5151
+ {
5152
+ value: includePageEnabled,
5153
+ loading: includePageLoading,
5154
+ disabled: includePageDisabled,
5155
+ onToggle: onIncludePageToggle
5156
+ }
5157
+ ), !disableImageAttachment && /* @__PURE__ */ React__default.createElement(React__default.Fragment, null, /* @__PURE__ */ React__default.createElement(
4993
5158
  "input",
4994
5159
  {
4995
5160
  type: "file",
@@ -5371,11 +5536,6 @@ const LoadingConversation = () => {
5371
5536
  );
5372
5537
  };
5373
5538
 
5374
- const FeatureFlagContext = createContext(void 0);
5375
- function FeatureFlagProvider({ children, flags }) {
5376
- return /* @__PURE__ */ React__default.createElement(FeatureFlagContext.Provider, { value: flags ?? {} }, children);
5377
- }
5378
-
5379
5539
  function useDebounce(value, delay) {
5380
5540
  const [debouncedValue, setDebouncedValue] = useState(value);
5381
5541
  useEffect(() => {
@@ -5486,7 +5646,8 @@ const ChatSearchComponent = forwardRef(
5486
5646
  secretAttributes,
5487
5647
  allowedRegions,
5488
5648
  style,
5489
- isSearchWidget = false
5649
+ isSearchWidget = false,
5650
+ isAgentAssist = false
5490
5651
  }, ref) => {
5491
5652
  const {
5492
5653
  answers,
@@ -5537,6 +5698,7 @@ const ChatSearchComponent = forwardRef(
5537
5698
  });
5538
5699
  const { scrollToLastAnswer, scrollToAnswer } = useScrollManager(answerRefs, containerRef, bottomRef);
5539
5700
  const { subscribeToStateChanges } = useSubscriptionManager();
5701
+ const { includePageEnabled, includePageLoading, includePageDisabled, handleIncludePageToggle, fetchPageContext } = useIncludePage({ isAgentAssist, apiKey: apiKey ?? "unknown", trackEvent });
5540
5702
  const loadFollowUpQuestions = async (searchQueryId, conversationId) => {
5541
5703
  if (!followUpQuestionsEndpoint || disableFollowUpQuestions) {
5542
5704
  return;
@@ -5662,7 +5824,8 @@ const ChatSearchComponent = forwardRef(
5662
5824
  };
5663
5825
  const generateAnswerForQuery = async ({
5664
5826
  searchQueryId,
5665
- conversationId
5827
+ conversationId,
5828
+ context
5666
5829
  }) => {
5667
5830
  try {
5668
5831
  const followUpQuestions = loadFollowUpQuestions(searchQueryId);
@@ -5673,7 +5836,8 @@ const ChatSearchComponent = forwardRef(
5673
5836
  type: "generate-for-query",
5674
5837
  conversationId,
5675
5838
  searchQueryId,
5676
- profileId: userData?.userId
5839
+ profileId: userData?.userId,
5840
+ ...context && { context }
5677
5841
  }
5678
5842
  });
5679
5843
  const reader = response.body?.getReader();
@@ -5820,6 +5984,7 @@ const ChatSearchComponent = forwardRef(
5820
5984
  );
5821
5985
  await Promise.resolve();
5822
5986
  followUpSearchRef.current?.focus();
5987
+ const pageContext = await fetchPageContext(conversationId, searchQuery);
5823
5988
  try {
5824
5989
  const attributes = { ...userData };
5825
5990
  const searchQueryId = await handleSearchApiCall({
@@ -5838,7 +6003,8 @@ const ChatSearchComponent = forwardRef(
5838
6003
  });
5839
6004
  await generateAnswerForQuery({
5840
6005
  searchQueryId,
5841
- conversationId
6006
+ conversationId,
6007
+ context: pageContext
5842
6008
  });
5843
6009
  } else {
5844
6010
  answerListDispatch(noArticlesFound());
@@ -6176,7 +6342,12 @@ const ChatSearchComponent = forwardRef(
6176
6342
  onRemoveImage: removeImage,
6177
6343
  isSearching,
6178
6344
  autocompleteSuggestions,
6179
- onAutocompleteSuggestionSelect: handleAutocompleteSuggestionClick
6345
+ onAutocompleteSuggestionSelect: handleAutocompleteSuggestionClick,
6346
+ isAgentAssist,
6347
+ includePageEnabled,
6348
+ includePageLoading,
6349
+ includePageDisabled,
6350
+ onIncludePageToggle: handleIncludePageToggle
6180
6351
  }
6181
6352
  )
6182
6353
  )
@@ -6307,4 +6478,4 @@ const ChatSearch = forwardRef(({ featureFlags, ...props }, ref) => /* @__PURE__
6307
6478
  ChatSearch.displayName = "ChatSearch";
6308
6479
 
6309
6480
  export { ChatSearch as C, ChatSearchProvider as a, useIsChatSearchDirty as b, useChatSearch as u };
6310
- //# sourceMappingURL=ChatSearch.BV8FTS2Y.js.map
6481
+ //# sourceMappingURL=ChatSearch.B4QTqo-0.js.map