@lobehub/lobehub 2.0.0-next.297 → 2.0.0-next.299

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 (88) hide show
  1. package/CHANGELOG.md +58 -0
  2. package/changelog/v1.json +18 -0
  3. package/package.json +2 -2
  4. package/src/app/[variants]/(main)/agent/_layout/Sidebar/Cron/Actions.tsx +4 -13
  5. package/src/app/[variants]/(main)/agent/_layout/Sidebar/Topic/Actions.tsx +4 -13
  6. package/src/app/[variants]/(main)/agent/_layout/Sidebar/Topic/index.tsx +2 -9
  7. package/src/app/[variants]/(main)/agent/features/Conversation/ConversationArea.tsx +2 -2
  8. package/src/app/[variants]/(main)/agent/features/Conversation/Header/Tags/KnowledgeTag.tsx +3 -4
  9. package/src/app/[variants]/(main)/agent/profile/features/ProfileEditor/MentionList/types.ts +4 -2
  10. package/src/app/[variants]/(main)/community/(detail)/group_agent/features/Details/Nav.tsx +0 -1
  11. package/src/app/[variants]/(main)/community/(detail)/group_agent/features/Details/Related/index.tsx +9 -5
  12. package/src/app/[variants]/(main)/community/(detail)/model/features/Sidebar/ActionButton/ChatWithModel.tsx +3 -8
  13. package/src/app/[variants]/(main)/community/(list)/assistant/features/MarketSourceSwitch.tsx +44 -23
  14. package/src/app/[variants]/(main)/community/(list)/features/SortButton/index.tsx +40 -19
  15. package/src/app/[variants]/(main)/group/_layout/Sidebar/Topic/Actions.tsx +4 -13
  16. package/src/app/[variants]/(main)/group/_layout/Sidebar/Topic/index.tsx +2 -9
  17. package/src/app/[variants]/(main)/group/features/Conversation/ConversationArea.tsx +2 -2
  18. package/src/app/[variants]/(main)/group/features/Conversation/Header/Tags/KnowledgeTag.tsx +3 -4
  19. package/src/app/[variants]/(main)/group/profile/features/AgentBuilder/AgentBuilderProvider.tsx +2 -2
  20. package/src/app/[variants]/(main)/group/profile/features/MemberProfile/MentionList/types.ts +4 -2
  21. package/src/app/[variants]/(main)/home/_layout/Body/Agent/Actions.tsx +3 -11
  22. package/src/app/[variants]/(main)/home/_layout/Body/Agent/List/Group/Actions.tsx +3 -12
  23. package/src/app/[variants]/(main)/home/_layout/Body/Agent/List/Group/Item.tsx +2 -9
  24. package/src/app/[variants]/(main)/home/_layout/Body/Agent/index.tsx +2 -9
  25. package/src/app/[variants]/(main)/home/_layout/Body/Project/index.tsx +2 -9
  26. package/src/app/[variants]/(main)/home/_layout/HomeAgentIdSync.tsx +23 -0
  27. package/src/app/[variants]/(main)/home/_layout/index.tsx +2 -0
  28. package/src/app/[variants]/(main)/home/features/CommunityAgents/index.tsx +11 -13
  29. package/src/app/[variants]/(main)/home/features/FeaturedPlugins/index.tsx +11 -13
  30. package/src/app/[variants]/(main)/home/features/RecentPage/index.tsx +12 -14
  31. package/src/app/[variants]/(main)/home/features/RecentResource/index.tsx +12 -14
  32. package/src/app/[variants]/(main)/memory/contexts/features/ContextDropdown.tsx +5 -3
  33. package/src/app/[variants]/(main)/memory/experiences/features/ExperienceDropdown.tsx +5 -3
  34. package/src/app/[variants]/(main)/memory/identities/features/IdentityDropdown.tsx +5 -3
  35. package/src/app/[variants]/(main)/memory/preferences/features/PreferenceDropdown.tsx +5 -3
  36. package/src/app/[variants]/(main)/page/_layout/Body/Actions.tsx +3 -13
  37. package/src/app/[variants]/(main)/page/_layout/Body/index.tsx +2 -9
  38. package/src/app/[variants]/(main)/resource/features/DndContextWrapper.tsx +1 -1
  39. package/src/app/[variants]/(main)/settings/profile/features/SSOProvidersList/index.tsx +3 -3
  40. package/src/app/[variants]/(main)/settings/provider/ProviderMenu/Actions.tsx +3 -11
  41. package/src/app/[variants]/(main)/settings/provider/ProviderMenu/List.tsx +12 -28
  42. package/src/app/[variants]/(main)/settings/provider/features/ModelList/DisabledModels.tsx +7 -8
  43. package/src/app/[variants]/(main)/settings/provider/features/ModelList/ModelTitle/index.tsx +18 -20
  44. package/src/app/[variants]/(mobile)/(home)/features/SessionListContent/CollapseGroup/Actions.tsx +10 -14
  45. package/src/app/[variants]/(mobile)/(home)/features/SessionListContent/List/Item/Actions.tsx +3 -13
  46. package/src/app/[variants]/share/t/[id]/SharedMessageList.tsx +2 -2
  47. package/src/business/server/lambda-routers/file.ts +1 -1
  48. package/src/features/AgentBuilder/AgentBuilderProvider.tsx +2 -2
  49. package/src/features/ChatInput/ActionBar/History/index.tsx +1 -1
  50. package/src/features/ChatInput/ActionBar/STT/common.tsx +1 -1
  51. package/src/features/ChatInput/ActionBar/Search/index.tsx +1 -1
  52. package/src/features/ChatInput/ActionBar/Upload/ServerMode.tsx +1 -0
  53. package/src/features/ChatInput/ActionBar/components/Action.tsx +4 -8
  54. package/src/features/ChatInput/ActionBar/components/ActionDropdown.tsx +225 -37
  55. package/src/features/Conversation/ConversationProvider.tsx +2 -1
  56. package/src/features/Conversation/Messages/Assistant/Actions/index.tsx +10 -6
  57. package/src/features/Conversation/Messages/AssistantGroup/Actions/index.tsx +10 -6
  58. package/src/features/Conversation/Messages/AssistantGroup/Tool/Detail/Intervention/ApprovalActions.tsx +11 -13
  59. package/src/features/Conversation/Messages/AssistantGroup/Tool/Detail/Intervention/ModeSelector.tsx +8 -10
  60. package/src/features/Conversation/Messages/Supervisor/Actions/index.tsx +10 -6
  61. package/src/features/Conversation/Messages/Task/Actions/index.tsx +10 -6
  62. package/src/features/Conversation/Messages/User/Actions/index.tsx +10 -6
  63. package/src/features/Conversation/StoreUpdater.tsx +1 -1
  64. package/src/features/Conversation/store/initialState.ts +3 -1
  65. package/src/features/Conversation/store/slices/data/action.ts +6 -5
  66. package/src/features/LibraryModal/AssignKnowledgeBase/Item/Action.tsx +23 -26
  67. package/src/features/ModelSwitchPanel/components/List/MultipleProvidersModelItem.tsx +16 -18
  68. package/src/features/ModelSwitchPanel/styles.ts +18 -1
  69. package/src/features/PageEditor/Copilot/AgentSelector/Actions.tsx +6 -13
  70. package/src/features/PageEditor/PageAgentProvider.tsx +2 -2
  71. package/src/features/PluginStore/InstalledList/List/Item/Action.tsx +33 -36
  72. package/src/features/PluginStore/McpList/List/Action.tsx +25 -28
  73. package/src/features/PluginStore/PluginList/List/Action.tsx +25 -28
  74. package/src/features/PluginTag/index.tsx +3 -4
  75. package/src/features/Portal/Artifacts/Body/Renderer/SVG.tsx +14 -11
  76. package/src/features/Portal/Thread/Chat/index.tsx +2 -2
  77. package/src/features/ProfileEditor/AgentTool.tsx +1 -1
  78. package/src/features/ResourceManager/components/Explorer/ToolBar/SortDropdown.tsx +21 -18
  79. package/src/features/ResourceManager/components/Explorer/ToolBar/ViewSwitcher.tsx +7 -13
  80. package/src/features/ResourceManager/components/Header/AddButton.tsx +4 -11
  81. package/src/features/User/UserPanel/LangButton.tsx +56 -44
  82. package/src/layout/AuthProvider/MarketAuth/MarketAuthProvider.tsx +1 -1
  83. package/src/services/discover.ts +6 -4
  84. package/src/services/document/index.ts +11 -1
  85. package/src/store/page/slices/crud/action.ts +0 -48
  86. package/src/store/tool/slices/lobehubSkillStore/action.ts +1 -2
  87. package/src/styles/global.ts +2 -2
  88. package/src/types/shim-lobe-ui.d.ts +7 -0
@@ -1,4 +1,4 @@
1
- import { ActionIcon, Button, Dropdown, Flexbox, Icon } from '@lobehub/ui';
1
+ import { ActionIcon, Button, DropdownMenu, Flexbox, Icon } from '@lobehub/ui';
2
2
  import { App } from 'antd';
3
3
  import { MoreVerticalIcon, Trash2 } from 'lucide-react';
4
4
  import { memo } from 'react';
@@ -31,37 +31,34 @@ const Actions = memo<ActionsProps>(({ identifier }) => {
31
31
  return (
32
32
  <Flexbox align={'center'} horizontal>
33
33
  {installed ? (
34
- <Dropdown
35
- menu={{
36
- items: [
37
- {
38
- danger: true,
39
- icon: <Icon icon={Trash2} />,
40
- key: 'uninstall',
41
- label: t('store.actions.uninstall'),
42
- onClick: () => {
43
- modal.confirm({
44
- centered: true,
45
- okButtonProps: { danger: true },
46
- onOk: async () => {
47
- // If plugin is enabled in current agent, disable it first
48
- if (isPluginEnabledInAgent) {
49
- await togglePlugin(identifier, false);
50
- }
51
- await unInstallPlugin(identifier);
52
- },
53
- title: t('store.actions.confirmUninstall'),
54
- type: 'error',
55
- });
56
- },
34
+ <DropdownMenu
35
+ items={[
36
+ {
37
+ danger: true,
38
+ icon: <Icon icon={Trash2} />,
39
+ key: 'uninstall',
40
+ label: t('store.actions.uninstall'),
41
+ onClick: () => {
42
+ modal.confirm({
43
+ centered: true,
44
+ okButtonProps: { danger: true },
45
+ onOk: async () => {
46
+ // If plugin is enabled in current agent, disable it first
47
+ if (isPluginEnabledInAgent) {
48
+ await togglePlugin(identifier, false);
49
+ }
50
+ await unInstallPlugin(identifier);
51
+ },
52
+ title: t('store.actions.confirmUninstall'),
53
+ type: 'error',
54
+ });
57
55
  },
58
- ],
59
- }}
56
+ },
57
+ ]}
60
58
  placement="bottomRight"
61
- trigger={['click']}
62
59
  >
63
60
  <ActionIcon icon={MoreVerticalIcon} loading={installing} />
64
- </Dropdown>
61
+ </DropdownMenu>
65
62
  ) : (
66
63
  <Button
67
64
  loading={installing}
@@ -1,7 +1,6 @@
1
1
  'use client';
2
2
 
3
- import { Dropdown, Icon, type MenuProps, Tag } from '@lobehub/ui';
4
- import { Center } from '@lobehub/ui';
3
+ import { Center, DropdownMenu, Icon, type MenuProps, Tag } from '@lobehub/ui';
5
4
  import isEqual from 'fast-deep-equal';
6
5
  import { LucideToyBrick } from 'lucide-react';
7
6
  import { memo } from 'react';
@@ -49,7 +48,7 @@ const PluginTag = memo<PluginTagProps>(({ plugins }) => {
49
48
  const count = plugins.length;
50
49
 
51
50
  return (
52
- <Dropdown menu={{ items }}>
51
+ <DropdownMenu items={items}>
53
52
  <div>
54
53
  <Tag>
55
54
  {<Icon icon={LucideToyBrick} />}
@@ -57,7 +56,7 @@ const PluginTag = memo<PluginTagProps>(({ plugins }) => {
57
56
  {count > 1 && <div>({plugins.length - 1}+)</div>}
58
57
  </Tag>
59
58
  </div>
60
- </Dropdown>
59
+ </DropdownMenu>
61
60
  );
62
61
  });
63
62
 
@@ -1,6 +1,6 @@
1
1
  import { BRANDING_NAME } from '@lobechat/business-const';
2
2
  import { copyImageToClipboard, sanitizeSVGContent } from '@lobechat/utils/client';
3
- import { Button, Center, Dropdown, Flexbox, Tooltip } from '@lobehub/ui';
3
+ import { Button, Center, DropdownMenu, Flexbox, Tooltip } from '@lobehub/ui';
4
4
  import { snapdom } from '@zumer/snapdom';
5
5
  import { App, Space } from 'antd';
6
6
  import { css, cx } from 'antd-style';
@@ -98,19 +98,22 @@ const SVGRenderer = ({ content }: SVGRendererProps) => {
98
98
  />
99
99
  <Flexbox className={cx(actions)}>
100
100
  <Space.Compact>
101
- <Dropdown
102
- menu={{
103
- items: [
104
- { key: 'png', label: t('artifacts.svg.download.png') },
105
- { key: 'svg', label: t('artifacts.svg.download.svg') },
106
- ],
107
- onClick: ({ key }) => {
108
- downloadImage(key);
101
+ <DropdownMenu
102
+ items={[
103
+ {
104
+ key: 'png',
105
+ label: t('artifacts.svg.download.png'),
106
+ onClick: () => downloadImage('png'),
109
107
  },
110
- }}
108
+ {
109
+ key: 'svg',
110
+ label: t('artifacts.svg.download.svg'),
111
+ onClick: () => downloadImage('svg'),
112
+ },
113
+ ]}
111
114
  >
112
115
  <Button icon={DownloadIcon} />
113
- </Dropdown>
116
+ </DropdownMenu>
114
117
  <Tooltip title={t('artifacts.svg.copyAsImage')}>
115
118
  <Button
116
119
  icon={CopyIcon}
@@ -204,8 +204,8 @@ const ThreadChat = memo(() => {
204
204
  hasInitMessages={!!messages}
205
205
  hooks={hooks}
206
206
  messages={messages}
207
- onMessagesChange={(msgs) => {
208
- replaceMessages(msgs, { context });
207
+ onMessagesChange={(msgs, ctx) => {
208
+ replaceMessages(msgs, { context: ctx });
209
209
  }}
210
210
  operationState={operationState}
211
211
  skipFetch={isCreatingNewThread}
@@ -617,7 +617,7 @@ const AgentTool = memo<AgentToolProps>(
617
617
  </div>
618
618
  </div>
619
619
  )}
620
- trigger={['click']}
620
+ trigger={'click'}
621
621
  >
622
622
  {button}
623
623
  </ActionDropdown>
@@ -1,9 +1,8 @@
1
- import { Dropdown } from '@lobehub/ui';
1
+ import { DropdownMenu, type DropdownMenuCheckboxItem } from '@lobehub/ui';
2
2
  import { ArrowDownAZ } from 'lucide-react';
3
3
  import { memo, useMemo } from 'react';
4
4
  import { useTranslation } from 'react-i18next';
5
5
 
6
- import { type MenuProps } from '@/components/Menu';
7
6
  import { useResourceManagerStore } from '@/app/[variants]/(main)/resource/features/store';
8
7
 
9
8
  import ActionIconWithChevron from './ActionIconWithChevron';
@@ -22,30 +21,34 @@ const SortDropdown = memo(() => {
22
21
  [t],
23
22
  );
24
23
 
25
- const menuItems: MenuProps['items'] = useMemo(
24
+ const selectedKey = sorter || 'createdAt';
25
+
26
+ const menuItems = useMemo<DropdownMenuCheckboxItem[]>(
26
27
  () =>
27
- sortOptions.map((option) => ({
28
- key: option.key,
29
- label: option.label,
30
- onClick: () => setSorter(option.key as 'name' | 'createdAt' | 'size'),
31
- })),
32
- [setSorter, sortOptions],
28
+ sortOptions.map(
29
+ (option): DropdownMenuCheckboxItem => ({
30
+ checked: option.key === selectedKey,
31
+ closeOnClick: true,
32
+ key: option.key,
33
+ label: option.label,
34
+ onCheckedChange: (checked: boolean) => {
35
+ if (checked) {
36
+ setSorter(option.key as 'name' | 'createdAt' | 'size');
37
+ }
38
+ },
39
+ type: 'checkbox',
40
+ }),
41
+ ),
42
+ [selectedKey, setSorter, sortOptions],
33
43
  );
34
44
 
35
45
  const currentSortLabel =
36
46
  sortOptions.find((option) => option.key === sorter)?.label || t('FileManager.sort.dateAdded');
37
47
 
38
48
  return (
39
- <Dropdown
40
- arrow={false}
41
- menu={{
42
- items: menuItems,
43
- selectable: true,
44
- selectedKeys: [sorter || 'createdAt'],
45
- }}
46
- >
49
+ <DropdownMenu items={menuItems}>
47
50
  <ActionIconWithChevron icon={ArrowDownAZ} title={currentSortLabel} />
48
- </Dropdown>
51
+ </DropdownMenu>
49
52
  );
50
53
  });
51
54
 
@@ -1,5 +1,5 @@
1
- import { Dropdown, Icon } from '@lobehub/ui';
2
- import { Grid3x3Icon, ListIcon } from 'lucide-react';
1
+ import { DropdownMenu, Icon } from '@lobehub/ui';
2
+ import { Check, Grid3x3Icon, ListIcon } from 'lucide-react';
3
3
  import { memo, useMemo } from 'react';
4
4
  import { useTranslation } from 'react-i18next';
5
5
 
@@ -23,33 +23,27 @@ const ViewSwitcher = memo(() => {
23
23
  const menuItems: MenuProps['items'] = useMemo(
24
24
  () => [
25
25
  {
26
+ extra: viewMode === 'list' ? <Icon icon={Check} /> : undefined,
26
27
  icon: <Icon icon={ListIcon} />,
27
28
  key: 'list',
28
29
  label: t('FileManager.view.list'),
29
30
  onClick: () => setViewMode('list'),
30
31
  },
31
32
  {
33
+ extra: viewMode === 'masonry' ? <Icon icon={Check} /> : undefined,
32
34
  icon: <Icon icon={Grid3x3Icon} />,
33
35
  key: 'masonry',
34
36
  label: t('FileManager.view.masonry'),
35
37
  onClick: () => setViewMode('masonry'),
36
38
  },
37
39
  ],
38
- [setViewMode, t],
40
+ [setViewMode, t, viewMode],
39
41
  );
40
42
 
41
43
  return (
42
- <Dropdown
43
- arrow={false}
44
- menu={{
45
- items: menuItems,
46
- selectable: true,
47
- selectedKeys: [viewMode],
48
- }}
49
- placement="bottomRight"
50
- >
44
+ <DropdownMenu items={menuItems} placement="bottomRight">
51
45
  <ActionIconWithChevron icon={currentViewIcon} title={currentViewLabel} />
52
- </Dropdown>
46
+ </DropdownMenu>
53
47
  );
54
48
  });
55
49
 
@@ -2,7 +2,7 @@
2
2
 
3
3
  import { FILE_URL } from '@lobechat/business-const';
4
4
  import { Notion } from '@lobehub/icons';
5
- import { Button, Dropdown, Icon, type MenuProps } from '@lobehub/ui';
5
+ import { Button, DropdownMenu, Icon, type MenuProps } from '@lobehub/ui';
6
6
  import { Upload } from 'antd';
7
7
  import { FilePenLine, FileUp, FolderIcon, FolderUp, Link, Plus } from 'lucide-react';
8
8
  import { useCallback, useMemo } from 'react';
@@ -211,18 +211,11 @@ const AddButton = () => {
211
211
 
212
212
  return (
213
213
  <>
214
- <Dropdown menu={{ items }} placement="bottomRight" trigger={['hover']}>
215
- <Button
216
- icon={Plus}
217
- onClick={(e) => {
218
- // Prevent default button behavior that might interfere with dropdown
219
- e.stopPropagation();
220
- }}
221
- type="primary"
222
- >
214
+ <DropdownMenu items={items} placement="bottomRight" trigger="both">
215
+ <Button data-no-highlight icon={Plus} type="primary">
223
216
  {t('addLibrary')}
224
217
  </Button>
225
- </Dropdown>
218
+ </DropdownMenu>
226
219
  <GuideModal
227
220
  cancelText={t('header.actions.notionGuide.cancel')}
228
221
  cover={<GuideVideo height={269} src={FILE_URL.importFromNotionGuide} width={358} />}
@@ -1,74 +1,86 @@
1
- import { ActionIcon, Dropdown, DropdownProps, Flexbox, Text } from '@lobehub/ui';
1
+ import {
2
+ ActionIcon,
3
+ DropdownMenu,
4
+ type DropdownMenuCheckboxItem,
5
+ type DropdownMenuProps,
6
+ Flexbox,
7
+ Text,
8
+ } from '@lobehub/ui';
2
9
  import { Languages } from 'lucide-react';
3
10
  import { memo, useMemo } from 'react';
4
11
  import { useTranslation } from 'react-i18next';
5
12
 
6
- import { type MenuProps } from '@/components/Menu';
7
13
  import { localeOptions } from '@/locales/resources';
8
14
  import { useGlobalStore } from '@/store/global';
9
15
  import { globalGeneralSelectors } from '@/store/global/selectors';
10
- import { type LocaleMode } from '@/types/locale';
11
16
 
12
- const LangButton = memo<{ placement?: DropdownProps['placement']; size?: number }>(
17
+ const LangButton = memo<{ placement?: DropdownMenuProps['placement']; size?: number }>(
13
18
  ({ placement, size }) => {
14
19
  const [language, switchLocale] = useGlobalStore((s) => [
15
20
  globalGeneralSelectors.language(s),
16
21
  s.switchLocale,
17
22
  ]);
18
23
 
19
- const handleLangChange = (value: LocaleMode) => {
20
- switchLocale(value);
21
- };
22
-
23
24
  const { t } = useTranslation(['setting', 'common']);
24
25
 
25
- const items: MenuProps['items'] = useMemo(
26
- () => [
27
- {
28
- key: 'auto',
29
- label: (
30
- <Flexbox gap={4}>
31
- <Text style={{ lineHeight: 1.2 }}>{t('settingCommon.lang.autoMode')}</Text>
32
- <Text fontSize={12} style={{ lineHeight: 1.2 }} type={'secondary'}>
33
- {t(`lang.auto` as any, { ns: 'common' })}
34
- </Text>
35
- </Flexbox>
36
- ),
37
- onClick: () => handleLangChange('auto'),
26
+ const items = useMemo<DropdownMenuCheckboxItem[]>(() => {
27
+ const autoItem: DropdownMenuCheckboxItem = {
28
+ checked: language === 'auto',
29
+ closeOnClick: true,
30
+ key: 'auto',
31
+ label: (
32
+ <Flexbox gap={4}>
33
+ <Text style={{ lineHeight: 1.2 }}>{t('settingCommon.lang.autoMode')}</Text>
34
+ <Text fontSize={12} style={{ lineHeight: 1.2 }} type={'secondary'}>
35
+ {t(`lang.auto` as any, { ns: 'common' })}
36
+ </Text>
37
+ </Flexbox>
38
+ ),
39
+ onCheckedChange: (checked: boolean) => {
40
+ if (checked) {
41
+ switchLocale('auto');
42
+ }
38
43
  },
39
- ...localeOptions.map((item) => ({
40
- key: item.value,
41
- label: (
42
- <Flexbox gap={4} key={item.value}>
43
- <Text style={{ lineHeight: 1.2 }}>{item.label}</Text>
44
- <Text fontSize={12} style={{ lineHeight: 1.2 }} type={'secondary'}>
45
- {t(`lang.${item.value}` as any, { ns: 'common' })}
46
- </Text>
47
- </Flexbox>
48
- ),
49
- onClick: () => handleLangChange(item.value),
50
- })),
51
- ],
52
- [t],
53
- );
44
+ type: 'checkbox',
45
+ };
46
+
47
+ const localeItems = localeOptions.map<DropdownMenuCheckboxItem>((item) => ({
48
+ checked: language === item.value,
49
+ closeOnClick: true,
50
+ key: item.value,
51
+ label: (
52
+ <Flexbox gap={4} key={item.value}>
53
+ <Text style={{ lineHeight: 1.2 }}>{item.label}</Text>
54
+ <Text fontSize={12} style={{ lineHeight: 1.2 }} type={'secondary'}>
55
+ {t(`lang.${item.value}` as any, { ns: 'common' })}
56
+ </Text>
57
+ </Flexbox>
58
+ ),
59
+ onCheckedChange: (checked: boolean) => {
60
+ if (checked) {
61
+ switchLocale(item.value);
62
+ }
63
+ },
64
+ type: 'checkbox',
65
+ }));
66
+
67
+ return [autoItem, ...localeItems];
68
+ }, [language, switchLocale, t]);
54
69
 
55
70
  return (
56
- <Dropdown
57
- arrow={false}
58
- menu={{
59
- items,
60
- selectable: true,
61
- selectedKeys: [language],
71
+ <DropdownMenu
72
+ items={items}
73
+ placement={placement}
74
+ popupProps={{
62
75
  style: {
63
76
  maxHeight: 360,
64
77
  minWidth: 240,
65
78
  overflow: 'auto',
66
79
  },
67
80
  }}
68
- placement={placement}
69
81
  >
70
82
  <ActionIcon icon={Languages} size={size || { blockSize: 32, size: 16 }} />
71
- </Dropdown>
83
+ </DropdownMenu>
72
84
  );
73
85
  },
74
86
  );
@@ -151,7 +151,7 @@ export const MarketAuthProvider = ({ children, isDesktop }: MarketAuthProviderPr
151
151
  null,
152
152
  );
153
153
  const [pendingProfileSuccessCallback, setPendingProfileSuccessCallback] = useState<
154
- ((profile: MarketUserProfile) => void) | null
154
+ ((_profile: MarketUserProfile) => void) | null
155
155
  >(null);
156
156
 
157
157
  // 订阅 user store 的初始化状态,当 isUserStateInit 为 true 时,settings 数据已加载完成
@@ -1,4 +1,8 @@
1
- import { type CategoryItem, type CategoryListQuery, type PluginManifest } from '@lobehub/market-sdk';
1
+ import {
2
+ type CategoryItem,
3
+ type CategoryListQuery,
4
+ type PluginManifest,
5
+ } from '@lobehub/market-sdk';
2
6
  import {
3
7
  AgentEventRequest,
4
8
  type CallReportRequest,
@@ -477,9 +481,7 @@ class DiscoverService {
477
481
  return lambdaClient.market.getGroupAgentIdentifiers.query();
478
482
  };
479
483
 
480
- getGroupAgentList = async (
481
- params: GroupAgentQueryParams = {},
482
- ): Promise<any> => {
484
+ getGroupAgentList = async (params: GroupAgentQueryParams = {}): Promise<any> => {
483
485
  const locale = globalHelpers.getCurrentLanguage();
484
486
  return lambdaClient.market.getGroupAgentList.query(
485
487
  {
@@ -2,6 +2,8 @@ import { type DocumentItem } from '@lobechat/database/schemas';
2
2
 
3
3
  import { lambdaClient } from '@/libs/trpc/client';
4
4
 
5
+ import { abortableRequest } from '../utils/abortableRequest';
6
+
5
7
  export interface CreateDocumentParams {
6
8
  content?: string;
7
9
  editorData: string;
@@ -41,7 +43,15 @@ export class DocumentService {
41
43
  return lambdaClient.document.queryDocuments.query(params);
42
44
  }
43
45
 
44
- async getDocumentById(id: string): Promise<DocumentItem | undefined> {
46
+ async getDocumentById(id: string, uniqueKey?: string): Promise<DocumentItem | undefined> {
47
+ if (uniqueKey) {
48
+ // Use fixed key so switching documents cancels the previous request
49
+ // This prevents race conditions where old document's data overwrites new document's editor
50
+ return abortableRequest.execute(uniqueKey, async (signal) =>
51
+ lambdaClient.document.getDocumentById.query({ id }, { signal }),
52
+ );
53
+ }
54
+
45
55
  return lambdaClient.document.getDocumentById.query({ id });
46
56
  }
47
57
 
@@ -47,10 +47,6 @@ export interface CrudAction {
47
47
  * Duplicate an existing page
48
48
  */
49
49
  duplicatePage: (pageId: string) => Promise<{ [key: string]: any; id: string }>;
50
- /**
51
- * Fetch full page detail by ID and update documents array
52
- */
53
- fetchPageDetail: (pageId: string) => Promise<void>;
54
50
  navigateToPage: (pageId: string | null) => void;
55
51
  /**
56
52
  * Remove a page (deletes from documents table)
@@ -240,50 +236,6 @@ export const createCrudSlice: StateCreator<
240
236
  return newPage;
241
237
  },
242
238
 
243
- fetchPageDetail: async (pageId) => {
244
- try {
245
- const document = await documentService.getDocumentById(pageId);
246
-
247
- if (!document) {
248
- console.warn(`[fetchPageDetail] Page not found: ${pageId}`);
249
- return;
250
- }
251
-
252
- const fullPage: LobeDocument = {
253
- content: document.content || null,
254
- createdAt: document.createdAt ? new Date(document.createdAt) : new Date(),
255
- editorData:
256
- typeof document.editorData === 'string'
257
- ? JSON.parse(document.editorData)
258
- : document.editorData || null,
259
- fileType: document.fileType,
260
- filename: document.title || document.filename || 'Untitled',
261
- id: document.id,
262
- metadata: document.metadata || {},
263
- source: 'document',
264
- sourceType: DocumentSourceType.EDITOR,
265
- title: document.title || '',
266
- totalCharCount: document.content?.length || 0,
267
- totalLineCount: 0,
268
- updatedAt: document.updatedAt ? new Date(document.updatedAt) : new Date(),
269
- };
270
-
271
- // Update document via internal dispatch
272
- const { documents } = get();
273
- if (documents?.some((doc) => doc.id === pageId)) {
274
- get().internal_dispatchDocuments({
275
- document: fullPage,
276
- id: pageId,
277
- type: 'updateDocument',
278
- });
279
- } else {
280
- get().internal_dispatchDocuments({ document: fullPage, type: 'addDocument' });
281
- }
282
- } catch (error) {
283
- console.error('[fetchPageDetail] Failed to fetch page:', error);
284
- }
285
- },
286
-
287
239
  navigateToPage: (pageId) => {
288
240
  if (!pageId) {
289
241
  get().navigate?.('/page');
@@ -315,11 +315,10 @@ export const createLobehubSkillStoreSlice: StateCreator<
315
315
  const response = await toolsClient.market.connectListConnections.query();
316
316
 
317
317
  // Debug logging
318
- console.log('[useFetchLobehubSkillConnections] raw response:', response);
319
318
 
320
319
  return response.connections.map((conn: any) => {
321
320
  // Debug logging for each connection
322
- console.log('[useFetchLobehubSkillConnections] connection:', conn);
321
+
323
322
  // Get provider config from local definition for correct display name
324
323
  const providerConfig = getLobehubSkillProviderById(conn.providerId);
325
324
  return {
@@ -55,8 +55,8 @@ export default ({ token }: { prefixCls: string; token: Theme }) => css`
55
55
  -webkit-app-region: no-drag;
56
56
  }
57
57
 
58
- .${CLASSNAMES.ContextTrigger}[data-popup-open],
59
- .${CLASSNAMES.DropdownMenuTrigger}[data-popup-open] {
58
+ .${CLASSNAMES.ContextTrigger}[data-popup-open]:not([data-no-highlight]),
59
+ .${CLASSNAMES.DropdownMenuTrigger}[data-popup-open]:not([data-no-highlight]) {
60
60
  background: ${token.colorFillTertiary};
61
61
  }
62
62
  `;
@@ -0,0 +1,7 @@
1
+ declare module '@lobehub/ui' {
2
+ export interface DropdownMenuProps {
3
+ 'data-no-highlight'?: boolean;
4
+ }
5
+ }
6
+
7
+ export {};