@lobehub/lobehub 2.0.0-next.12 → 2.0.0-next.14

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 (212) hide show
  1. package/CHANGELOG.md +50 -0
  2. package/changelog/v1.json +18 -0
  3. package/package.json +1 -1
  4. package/packages/const/src/version.ts +3 -3
  5. package/packages/database/src/repositories/dataImporter/deprecated/__tests__/index.test.ts +2 -1
  6. package/packages/database/src/repositories/dataImporter/deprecated/index.ts +7 -1
  7. package/src/app/[variants]/(main)/(mobile)/me/(home)/__tests__/useCategory.test.tsx +9 -0
  8. package/src/app/[variants]/(main)/(mobile)/me/(home)/layout.tsx +0 -2
  9. package/src/app/[variants]/(main)/chat/@session/features/SessionListContent/List/Item/Actions.tsx +3 -28
  10. package/src/app/[variants]/(main)/chat/_layout/Desktop/index.tsx +0 -2
  11. package/src/app/[variants]/(main)/chat/_layout/Mobile.tsx +1 -5
  12. package/src/app/[variants]/(main)/chat/settings/features/HeaderContent.tsx +2 -62
  13. package/src/app/[variants]/(main)/image/features/PromptInput/index.tsx +1 -1
  14. package/src/app/[variants]/(main)/image/page.tsx +0 -2
  15. package/src/app/[variants]/(main)/profile/_layout/Desktop/index.tsx +23 -24
  16. package/src/app/[variants]/(main)/profile/_layout/Mobile/index.tsx +5 -9
  17. package/src/app/[variants]/(main)/settings/_layout/Desktop/index.tsx +0 -2
  18. package/src/app/[variants]/(main)/settings/_layout/Mobile/index.tsx +0 -2
  19. package/src/app/[variants]/(main)/settings/provider/(list)/ProviderGrid/Card.tsx +1 -1
  20. package/src/app/[variants]/loading/index.tsx +1 -10
  21. package/src/components/Link.tsx +12 -0
  22. package/src/envs/app.ts +5 -8
  23. package/src/features/DataImporter/index.tsx +15 -60
  24. package/src/features/DevPanel/PostgresViewer/usePgTable.ts +3 -2
  25. package/src/hooks/useInterceptingRoutes.test.ts +21 -3
  26. package/src/libs/trpc/client/index.ts +0 -1
  27. package/src/libs/trpc/client/lambda.ts +8 -5
  28. package/src/libs/trpc/lambda/context.ts +4 -1
  29. package/src/server/routers/desktop/mcp.ts +1 -3
  30. package/src/server/routers/lambda/config/index.test.ts +2 -2
  31. package/src/server/routers/tools/mcp.ts +2 -3
  32. package/src/server/routers/tools/search.test.ts +1 -7
  33. package/src/server/routers/tools/search.ts +1 -4
  34. package/src/services/__tests__/tool.test.ts +0 -3
  35. package/src/services/aiModel/index.test.ts +0 -3
  36. package/src/services/aiModel/index.ts +1 -7
  37. package/src/services/aiProvider/index.test.ts +0 -3
  38. package/src/services/aiProvider/index.ts +1 -7
  39. package/src/services/chatGroup/index.ts +1 -10
  40. package/src/services/config.ts +1 -65
  41. package/src/services/export/index.ts +1 -4
  42. package/src/services/file/index.ts +1 -11
  43. package/src/services/import/index.ts +1 -7
  44. package/src/services/message/index.ts +1 -11
  45. package/src/services/plugin/index.ts +1 -11
  46. package/src/services/session/index.ts +1 -11
  47. package/src/services/tableViewer/client.ts +12 -15
  48. package/src/services/thread/index.ts +1 -7
  49. package/src/services/topic/index.ts +1 -11
  50. package/src/services/user/index.ts +1 -13
  51. package/src/store/chat/slices/aiChat/actions/__tests__/generateAIChat.test.ts +0 -241
  52. package/src/store/chat/slices/aiChat/actions/__tests__/generateAIChatV2.test.ts +26 -1
  53. package/src/store/chat/slices/aiChat/actions/__tests__/helpers.ts +3 -1
  54. package/src/store/chat/slices/aiChat/actions/generateAIChat.ts +1 -138
  55. package/src/store/user/slices/common/action.test.ts +1 -4
  56. package/src/app/(backend)/trpc/edge/[trpc]/route.ts +0 -26
  57. package/src/app/[variants]/(main)/(mobile)/me/data/features/Category.tsx +0 -48
  58. package/src/app/[variants]/(main)/(mobile)/me/data/features/Header.tsx +0 -33
  59. package/src/app/[variants]/(main)/(mobile)/me/data/layout.tsx +0 -13
  60. package/src/app/[variants]/(main)/(mobile)/me/data/loading.tsx +0 -5
  61. package/src/app/[variants]/(main)/(mobile)/me/data/page.tsx +0 -29
  62. package/src/app/[variants]/(main)/chat/features/Migration/DBReader.ts +0 -290
  63. package/src/app/[variants]/(main)/chat/features/Migration/ExportConfigButton.tsx +0 -35
  64. package/src/app/[variants]/(main)/chat/features/Migration/Failed.tsx +0 -120
  65. package/src/app/[variants]/(main)/chat/features/Migration/Modal.tsx +0 -81
  66. package/src/app/[variants]/(main)/chat/features/Migration/Start.tsx +0 -108
  67. package/src/app/[variants]/(main)/chat/features/Migration/UpgradeButton.tsx +0 -71
  68. package/src/app/[variants]/(main)/chat/features/Migration/const.ts +0 -15
  69. package/src/app/[variants]/(main)/chat/features/Migration/index.tsx +0 -50
  70. package/src/app/[variants]/loading/Client/Content.tsx +0 -48
  71. package/src/app/[variants]/loading/Client/Error.tsx +0 -27
  72. package/src/app/[variants]/loading/Client/Redirect.tsx +0 -47
  73. package/src/app/[variants]/loading/Client/index.tsx +0 -22
  74. package/src/components/InnerLink.tsx +0 -20
  75. package/src/database/_deprecated/core/__tests__/db-upgrade.test.ts +0 -42
  76. package/src/database/_deprecated/core/__tests__/db.test.ts +0 -79
  77. package/src/database/_deprecated/core/__tests__/model.test.ts +0 -55
  78. package/src/database/_deprecated/core/db.ts +0 -246
  79. package/src/database/_deprecated/core/index.ts +0 -2
  80. package/src/database/_deprecated/core/migrations/migrateSettingsToUser/fixtures/input.json +0 -55
  81. package/src/database/_deprecated/core/migrations/migrateSettingsToUser/fixtures/output.json +0 -60
  82. package/src/database/_deprecated/core/migrations/migrateSettingsToUser/index.test.ts +0 -14
  83. package/src/database/_deprecated/core/migrations/migrateSettingsToUser/index.ts +0 -22
  84. package/src/database/_deprecated/core/migrations/migrateSettingsToUser/type.ts +0 -105
  85. package/src/database/_deprecated/core/model.ts +0 -218
  86. package/src/database/_deprecated/core/schemas.ts +0 -88
  87. package/src/database/_deprecated/core/types/db.ts +0 -15
  88. package/src/database/_deprecated/models/__DEBUG.ts +0 -124
  89. package/src/database/_deprecated/models/__tests__/file.test.ts +0 -83
  90. package/src/database/_deprecated/models/__tests__/message.test.ts +0 -426
  91. package/src/database/_deprecated/models/__tests__/plugin.test.ts +0 -81
  92. package/src/database/_deprecated/models/__tests__/session.test.ts +0 -253
  93. package/src/database/_deprecated/models/__tests__/sessionGroup.test.ts +0 -220
  94. package/src/database/_deprecated/models/__tests__/topic.test.ts +0 -523
  95. package/src/database/_deprecated/models/__tests__/user.test.ts +0 -82
  96. package/src/database/_deprecated/models/file.ts +0 -51
  97. package/src/database/_deprecated/models/message.ts +0 -277
  98. package/src/database/_deprecated/models/plugin.ts +0 -62
  99. package/src/database/_deprecated/models/session.ts +0 -271
  100. package/src/database/_deprecated/models/sessionGroup.ts +0 -93
  101. package/src/database/_deprecated/models/topic.ts +0 -250
  102. package/src/database/_deprecated/models/user.ts +0 -69
  103. package/src/database/_deprecated/schemas/files.ts +0 -39
  104. package/src/database/_deprecated/schemas/message.ts +0 -50
  105. package/src/database/_deprecated/schemas/plugin.ts +0 -12
  106. package/src/database/_deprecated/schemas/session.ts +0 -54
  107. package/src/database/_deprecated/schemas/sessionGroup.ts +0 -8
  108. package/src/database/_deprecated/schemas/topic.ts +0 -12
  109. package/src/database/_deprecated/schemas/user.ts +0 -40
  110. package/src/features/DataImporter/_deprecated.ts +0 -43
  111. package/src/features/InitClientDB/EnableModal.tsx +0 -118
  112. package/src/features/InitClientDB/ErrorResult.tsx +0 -143
  113. package/src/features/InitClientDB/InitIndicator.tsx +0 -124
  114. package/src/features/InitClientDB/PGliteIcon.tsx +0 -28
  115. package/src/features/InitClientDB/features/DatabaseRepair/Backup.tsx +0 -75
  116. package/src/features/InitClientDB/features/DatabaseRepair/Diagnosis.tsx +0 -98
  117. package/src/features/InitClientDB/features/DatabaseRepair/Repair.tsx +0 -218
  118. package/src/features/InitClientDB/features/DatabaseRepair/index.tsx +0 -91
  119. package/src/features/InitClientDB/index.tsx +0 -37
  120. package/src/libs/trpc/client/edge.ts +0 -26
  121. package/src/libs/trpc/edge/context.ts +0 -71
  122. package/src/libs/trpc/edge/index.ts +0 -45
  123. package/src/libs/trpc/edge/init.ts +0 -26
  124. package/src/libs/trpc/edge/middleware/jwtPayload.test.ts +0 -75
  125. package/src/libs/trpc/edge/middleware/jwtPayload.ts +0 -14
  126. package/src/migrations/FromV0ToV1.ts +0 -10
  127. package/src/migrations/FromV1ToV2/fixtures/input-v1-session.json +0 -191
  128. package/src/migrations/FromV1ToV2/fixtures/output-v2.json +0 -202
  129. package/src/migrations/FromV1ToV2/index.ts +0 -82
  130. package/src/migrations/FromV1ToV2/migrations.test.ts +0 -224
  131. package/src/migrations/FromV1ToV2/types/v1.ts +0 -78
  132. package/src/migrations/FromV1ToV2/types/v2.ts +0 -52
  133. package/src/migrations/FromV2ToV3/fixtures/input-v2-session.json +0 -72
  134. package/src/migrations/FromV2ToV3/fixtures/output-v3-from-v1.json +0 -203
  135. package/src/migrations/FromV2ToV3/fixtures/output-v3.json +0 -74
  136. package/src/migrations/FromV2ToV3/index.ts +0 -30
  137. package/src/migrations/FromV2ToV3/migrations.test.ts +0 -42
  138. package/src/migrations/FromV2ToV3/types/v3.ts +0 -27
  139. package/src/migrations/FromV3ToV4/fixtures/azure-input-v3.json +0 -79
  140. package/src/migrations/FromV3ToV4/fixtures/azure-output-v4.json +0 -75
  141. package/src/migrations/FromV3ToV4/fixtures/ollama-input-v3.json +0 -85
  142. package/src/migrations/FromV3ToV4/fixtures/ollama-output-v4.json +0 -86
  143. package/src/migrations/FromV3ToV4/fixtures/openai-input-v3.json +0 -77
  144. package/src/migrations/FromV3ToV4/fixtures/openai-output-v4.json +0 -77
  145. package/src/migrations/FromV3ToV4/fixtures/openrouter-input-v3.json +0 -82
  146. package/src/migrations/FromV3ToV4/fixtures/openrouter-output-v4.json +0 -85
  147. package/src/migrations/FromV3ToV4/fixtures/output-v4-from-v1.json +0 -203
  148. package/src/migrations/FromV3ToV4/index.ts +0 -102
  149. package/src/migrations/FromV3ToV4/migrations.test.ts +0 -195
  150. package/src/migrations/FromV3ToV4/types/v3.ts +0 -52
  151. package/src/migrations/FromV3ToV4/types/v4.ts +0 -37
  152. package/src/migrations/FromV4ToV5/fixtures/from-v1-to-v5-output.json +0 -245
  153. package/src/migrations/FromV4ToV5/fixtures/function-input-v4.json +0 -96
  154. package/src/migrations/FromV4ToV5/fixtures/function-output-v5.json +0 -120
  155. package/src/migrations/FromV4ToV5/index.ts +0 -58
  156. package/src/migrations/FromV4ToV5/migrations.test.ts +0 -49
  157. package/src/migrations/FromV4ToV5/types/v4.ts +0 -21
  158. package/src/migrations/FromV4ToV5/types/v5.ts +0 -27
  159. package/src/migrations/FromV5ToV6/fixtures/from-v1-to-v6-output.json +0 -247
  160. package/src/migrations/FromV5ToV6/fixtures/session-input-v5.json +0 -81
  161. package/src/migrations/FromV5ToV6/fixtures/session-output-v6.json +0 -85
  162. package/src/migrations/FromV5ToV6/index.ts +0 -61
  163. package/src/migrations/FromV5ToV6/migrations.test.ts +0 -50
  164. package/src/migrations/FromV5ToV6/types/v5.ts +0 -48
  165. package/src/migrations/FromV5ToV6/types/v6.ts +0 -63
  166. package/src/migrations/FromV6ToV7/fixtures/output-v7-from-v1.json +0 -203
  167. package/src/migrations/FromV6ToV7/fixtures/provider-input-v6.json +0 -103
  168. package/src/migrations/FromV6ToV7/fixtures/provider-output-v7.json +0 -118
  169. package/src/migrations/FromV6ToV7/index.ts +0 -101
  170. package/src/migrations/FromV6ToV7/migrations.test.ts +0 -64
  171. package/src/migrations/FromV6ToV7/types/v6.ts +0 -61
  172. package/src/migrations/FromV6ToV7/types/v7.ts +0 -69
  173. package/src/migrations/VersionController.test.ts +0 -88
  174. package/src/migrations/VersionController.ts +0 -67
  175. package/src/migrations/index.ts +0 -61
  176. package/src/server/routers/edge/appStatus.ts +0 -3
  177. package/src/server/routers/edge/index.ts +0 -14
  178. package/src/server/routers/edge/upload.ts +0 -16
  179. package/src/services/aiModel/client.ts +0 -70
  180. package/src/services/aiProvider/client.ts +0 -58
  181. package/src/services/baseClientService/index.ts +0 -9
  182. package/src/services/chatGroup/client.ts +0 -63
  183. package/src/services/export/_deprecated.ts +0 -155
  184. package/src/services/export/client.ts +0 -15
  185. package/src/services/file/_deprecated.test.ts +0 -119
  186. package/src/services/file/_deprecated.ts +0 -80
  187. package/src/services/file/client.test.ts +0 -199
  188. package/src/services/file/client.ts +0 -85
  189. package/src/services/import/_deprecated.ts +0 -115
  190. package/src/services/import/client.test.ts +0 -1015
  191. package/src/services/import/client.ts +0 -64
  192. package/src/services/message/_deprecated.test.ts +0 -398
  193. package/src/services/message/_deprecated.ts +0 -168
  194. package/src/services/message/client.test.ts +0 -410
  195. package/src/services/message/client.ts +0 -192
  196. package/src/services/plugin/_deprecated.test.ts +0 -162
  197. package/src/services/plugin/_deprecated.ts +0 -42
  198. package/src/services/plugin/client.test.ts +0 -177
  199. package/src/services/plugin/client.ts +0 -46
  200. package/src/services/session/_deprecated.test.ts +0 -440
  201. package/src/services/session/_deprecated.ts +0 -190
  202. package/src/services/session/client.test.ts +0 -413
  203. package/src/services/session/client.ts +0 -193
  204. package/src/services/thread/client.ts +0 -51
  205. package/src/services/topic/_deprecated.test.ts +0 -245
  206. package/src/services/topic/_deprecated.ts +0 -75
  207. package/src/services/topic/client.ts +0 -89
  208. package/src/services/topic/pglite.test.ts +0 -212
  209. package/src/services/user/_deprecated.test.ts +0 -101
  210. package/src/services/user/_deprecated.ts +0 -70
  211. package/src/services/user/client.test.ts +0 -111
  212. package/src/services/user/client.ts +0 -104
@@ -1,15 +0,0 @@
1
- export const MIGRATE_KEY = 'migrated';
2
- export enum UpgradeStatus {
3
- START,
4
- UPGRADING,
5
- UPGRADED,
6
- UPGRADE_FAILED,
7
- }
8
-
9
- export const V1DB_NAME = 'LobeHub';
10
- export const V1DB_TABLE_NAME = 'LOBE_CHAT';
11
-
12
- export interface MigrationError {
13
- message: string;
14
- stack: string;
15
- }
@@ -1,50 +0,0 @@
1
- 'use client';
2
-
3
- import { Spin } from 'antd';
4
- import dynamic from 'next/dynamic';
5
- import { memo, useEffect, useState } from 'react';
6
-
7
- import { isServerMode } from '@/const/version';
8
- import { useGlobalStore } from '@/store/global';
9
- import { systemStatusSelectors } from '@/store/global/selectors';
10
-
11
- import { V2DBReader } from './DBReader';
12
-
13
- const Modal = dynamic(() => import('./Modal'), { loading: () => <Spin fullscreen />, ssr: false });
14
-
15
- const Migration = memo(() => {
16
- const [dbState, setDbState] = useState(null);
17
- const [open, setOpen] = useState(false);
18
-
19
- const isPgliteInited = useGlobalStore(systemStatusSelectors.isPgliteInited);
20
-
21
- const checkMigration = async () => {
22
- const isMigrated = localStorage.getItem('V2DB_IS_MIGRATED');
23
- // if db have migrated already, don't show modal
24
- if (isMigrated || isServerMode) return;
25
-
26
- const dbReader = new V2DBReader([
27
- 'messages',
28
- 'files',
29
- 'plugins',
30
- 'sessionGroups',
31
- 'sessions',
32
- 'topics',
33
- 'users',
34
- ]);
35
- const data = await dbReader.readAllData();
36
- console.log('migration data:', data);
37
- const state = await dbReader.convertToImportData(data);
38
- console.log('import state', state);
39
- setDbState(state as any);
40
- setOpen(true);
41
- };
42
-
43
- useEffect(() => {
44
- if (isPgliteInited) checkMigration();
45
- }, [isPgliteInited]);
46
-
47
- return open && <Modal open={open} setOpen={setOpen} state={dbState} />;
48
- });
49
-
50
- export default Migration;
@@ -1,48 +0,0 @@
1
- import dynamic from 'next/dynamic';
2
- import React, { memo } from 'react';
3
- import { useTranslation } from 'react-i18next';
4
-
5
- import FullscreenLoading from '@/components/Loading/FullscreenLoading';
6
- import { useGlobalStore } from '@/store/global';
7
- import { systemStatusSelectors } from '@/store/global/selectors';
8
- import { DatabaseLoadingState } from '@/types/clientDB';
9
-
10
- import { CLIENT_LOADING_STAGES } from '../stage';
11
-
12
- const InitError = dynamic(() => import('./Error'), { ssr: false });
13
-
14
- interface InitProps {
15
- setActiveStage: (value: string) => void;
16
- }
17
-
18
- const Init = memo<InitProps>(({ setActiveStage }) => {
19
- const useInitClientDB = useGlobalStore((s) => s.useInitClientDB);
20
-
21
- useInitClientDB({ onStateChange: setActiveStage });
22
-
23
- return null;
24
- });
25
-
26
- interface ContentProps {
27
- loadingStage: string;
28
- setActiveStage: (value: string) => void;
29
- }
30
-
31
- const Content = memo<ContentProps>(({ loadingStage, setActiveStage }) => {
32
- const { t } = useTranslation('common');
33
- const isPgliteNotInited = useGlobalStore(systemStatusSelectors.isPgliteNotInited);
34
- const isError = useGlobalStore((s) => s.initClientDBStage === DatabaseLoadingState.Error);
35
-
36
- return (
37
- <>
38
- {isPgliteNotInited && <Init setActiveStage={setActiveStage} />}
39
- <FullscreenLoading
40
- activeStage={CLIENT_LOADING_STAGES.indexOf(loadingStage)}
41
- contentRender={isError && <InitError />}
42
- stages={CLIENT_LOADING_STAGES.map((key) => t(`appLoading.${key}` as any))}
43
- />
44
- </>
45
- );
46
- });
47
-
48
- export default Content;
@@ -1,27 +0,0 @@
1
- import { Button } from '@lobehub/ui';
2
- import React from 'react';
3
- import { useTranslation } from 'react-i18next';
4
- import { Center } from 'react-layout-kit';
5
-
6
- import ErrorResult from '@/features/InitClientDB/ErrorResult';
7
-
8
- const InitError = () => {
9
- const { t } = useTranslation('common');
10
-
11
- return (
12
- <ErrorResult>
13
- {({ setOpen }) => (
14
- <Center gap={8}>
15
- {t('appLoading.failed')}
16
- <div>
17
- <Button onClick={() => setOpen(true)} type={'primary'}>
18
- {t('appLoading.showDetail')}
19
- </Button>
20
- </div>
21
- </Center>
22
- )}
23
- </ErrorResult>
24
- );
25
- };
26
-
27
- export default InitError;
@@ -1,47 +0,0 @@
1
- 'use client';
2
-
3
- import { useRouter } from 'next/navigation';
4
- import { memo, useEffect } from 'react';
5
-
6
- import { useGlobalStore } from '@/store/global';
7
- import { systemStatusSelectors } from '@/store/global/selectors';
8
- import { useUserStore } from '@/store/user';
9
-
10
- import { AppLoadingStage } from '../stage';
11
-
12
- interface RedirectProps {
13
- setActiveStage: (value: AppLoadingStage) => void;
14
- }
15
-
16
- const Redirect = memo<RedirectProps>(({ setActiveStage }) => {
17
- const router = useRouter();
18
- const isUserStateInit = useUserStore((s) => s.isUserStateInit);
19
-
20
- const isPgliteNotEnabled = useGlobalStore(systemStatusSelectors.isPgliteNotEnabled);
21
-
22
- const navToChat = () => {
23
- setActiveStage(AppLoadingStage.GoToChat);
24
- router.replace('/chat');
25
- };
26
-
27
- useEffect(() => {
28
- // if pglite is not enabled, redirect to chat
29
- if (isPgliteNotEnabled) {
30
- navToChat();
31
- return;
32
- }
33
-
34
- // if user state not init, wait for loading
35
- if (!isUserStateInit) {
36
- setActiveStage(AppLoadingStage.InitUser);
37
- return;
38
- }
39
-
40
- // finally check the conversation status
41
- navToChat();
42
- }, [isUserStateInit, isPgliteNotEnabled]);
43
-
44
- return null;
45
- });
46
-
47
- export default Redirect;
@@ -1,22 +0,0 @@
1
- 'use client';
2
-
3
- import { useState } from 'react';
4
-
5
- import { AppLoadingStage } from '../stage';
6
- import Content from './Content';
7
- import Redirect from './Redirect';
8
-
9
- const ClientMode = () => {
10
- const [activeStage, setActiveStage] = useState<string>(AppLoadingStage.Initializing);
11
-
12
- return (
13
- <>
14
- <Content loadingStage={activeStage} setActiveStage={setActiveStage} />
15
- <Redirect setActiveStage={setActiveStage} />
16
- </>
17
- );
18
- };
19
-
20
- ClientMode.displayName = 'ClientMode';
21
-
22
- export default ClientMode;
@@ -1,20 +0,0 @@
1
- 'use client';
2
-
3
- import Link, { LinkProps } from 'next/link';
4
- import { AnchorHTMLAttributes, ReactNode } from 'react';
5
-
6
- import { useServerConfigStore } from '@/store/serverConfig';
7
-
8
- interface InnerLinkProps
9
- extends Omit<AnchorHTMLAttributes<HTMLAnchorElement>, keyof LinkProps>,
10
- LinkProps {
11
- children?: ReactNode | undefined;
12
- }
13
-
14
- const InnerLink = ({ href, ...props }: InnerLinkProps) => {
15
- const variants = useServerConfigStore((s) => s.segmentVariants);
16
-
17
- return <Link {...props} as={href} href={`/${variants}${href}`} />;
18
- };
19
-
20
- export default InnerLink;
@@ -1,42 +0,0 @@
1
- import Dexie from 'dexie';
2
- import { afterEach, beforeEach, describe, expect, it } from 'vitest';
3
-
4
- import { BrowserDB } from '../db';
5
- import { dbSchemaV3 } from '../schemas';
6
- import { LOBE_CHAT_LOCAL_DB_NAME } from '../types/db';
7
-
8
- beforeEach(async () => {
9
- // 确保在测试开始前删除数据库
10
- await Dexie.delete(LOBE_CHAT_LOCAL_DB_NAME);
11
- });
12
-
13
- afterEach(async () => {
14
- // 确保在测试结束后删除数据库
15
- await Dexie.delete(LOBE_CHAT_LOCAL_DB_NAME);
16
- });
17
-
18
- describe('LocalDB migration', () => {
19
- it('should upgrade from version 3 to version 4 correctly', async () => {
20
- // 使用版本3的schema创建数据库实例并填充测试数据
21
- const dbV3 = new Dexie(LOBE_CHAT_LOCAL_DB_NAME);
22
- dbV3.version(3).stores(dbSchemaV3);
23
- await dbV3.open();
24
- await dbV3.table('sessions').bulkAdd([
25
- { id: 's1', group: 'pinned' },
26
- { id: 's2', group: 'default' },
27
- ]);
28
- dbV3.close();
29
-
30
- // 创建新的数据库实例,包含版本4的迁移逻辑
31
- const dbV4 = new BrowserDB();
32
- await dbV4.open();
33
-
34
- // 验证迁移后的数据
35
- const updatedSession1 = await dbV4.sessions.get('s1');
36
- const updatedSession2 = await dbV4.sessions.get('s2');
37
- expect(updatedSession1).toEqual({ id: 's1', pinned: 1, group: 'default' });
38
- expect(updatedSession2).toEqual({ id: 's2', pinned: 0, group: 'default' });
39
-
40
- dbV4.close();
41
- });
42
- });
@@ -1,79 +0,0 @@
1
- import { afterEach, beforeEach, describe, expect, it } from 'vitest';
2
-
3
- import { DB_File } from '../../schemas/files';
4
- import { BrowserDB } from '../db';
5
- import { DBModel } from '../types/db';
6
-
7
- describe('LocalDB', () => {
8
- let db: BrowserDB;
9
-
10
- beforeEach(() => {
11
- db = new BrowserDB();
12
- });
13
-
14
- afterEach(async () => {
15
- await db.delete();
16
- db.close();
17
- });
18
-
19
- it('should be instantiated with the correct schema', () => {
20
- const filesTable = db.files;
21
-
22
- expect(filesTable).toBeDefined();
23
- });
24
-
25
- it('should allow adding a file', async () => {
26
- const file: DBModel<DB_File> = {
27
- id: 'file1',
28
- name: 'testfile.txt',
29
- data: new ArrayBuffer(3),
30
- saveMode: 'local',
31
- fileType: 'plain/text',
32
- size: 3,
33
- createdAt: Date.now(),
34
- updatedAt: Date.now(),
35
- };
36
-
37
- await db.files.add(file);
38
-
39
- expect(await db.files.get(file.id)).toEqual(file);
40
- });
41
-
42
- it('should allow updating a file', async () => {
43
- const file: DBModel<DB_File> = {
44
- id: 'file1',
45
- name: 'testfile.txt',
46
- data: new ArrayBuffer(3),
47
- saveMode: 'local',
48
- fileType: 'plain/text',
49
- size: 3,
50
- createdAt: Date.now(),
51
- updatedAt: Date.now(),
52
- };
53
- await db.files.add(file);
54
-
55
- // Act
56
- await db.files.update(file.id, { name: 'update.txt' });
57
-
58
- // Assert
59
- expect(await db.files.get(file.id)).toHaveProperty('name', 'update.txt');
60
- });
61
-
62
- it('should allow deleting a file', async () => {
63
- const file: DBModel<DB_File> = {
64
- id: 'file1',
65
- name: 'testfile.txt',
66
- data: new ArrayBuffer(3),
67
- saveMode: 'local',
68
- fileType: 'plain/text',
69
- size: 3,
70
- updatedAt: Date.now(),
71
- createdAt: Date.now(),
72
- };
73
- await db.files.add(file);
74
-
75
- await db.files.delete(file.id);
76
-
77
- expect(await db.files.get(file.id)).toBeUndefined();
78
- });
79
- });
@@ -1,55 +0,0 @@
1
- import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest';
2
- import { z } from 'zod';
3
-
4
- import { BaseModel } from '../model';
5
-
6
- // Define a mock schema for testing
7
- const mockSchema = z.object({
8
- name: z.string(),
9
- content: z.string(),
10
- });
11
-
12
- // Define a mock table name
13
- const mockTableName = 'files';
14
-
15
- describe('BaseModel', () => {
16
- let baseModel: BaseModel<typeof mockTableName>;
17
-
18
- beforeEach(() => {
19
- baseModel = new BaseModel(mockTableName, mockSchema);
20
- // Mock the console.error to test error logging
21
- vi.spyOn(console, 'error').mockImplementation(() => {});
22
- });
23
-
24
- afterEach(() => {
25
- vi.restoreAllMocks();
26
- // console.error = originalConsoleError;
27
- });
28
-
29
- it('should have a table property', () => {
30
- expect(baseModel.table).toBeDefined();
31
- });
32
-
33
- describe('add method', () => {
34
- it('should add a valid record to the database', async () => {
35
- const validData = {
36
- name: 'testfile.txt',
37
- content: 'Hello, World!',
38
- };
39
-
40
- const result = await baseModel['_addWithSync'](validData);
41
-
42
- expect(result).toHaveProperty('id');
43
- expect(console.error).not.toHaveBeenCalled();
44
- });
45
-
46
- it('should throw an error and log to console when adding an invalid record', async () => {
47
- const invalidData = {
48
- name: 123, // Invalid type, should be a string
49
- content: 'Hello, World!',
50
- };
51
-
52
- await expect(baseModel['_addWithSync'](invalidData)).rejects.toThrow(TypeError);
53
- });
54
- });
55
- });
@@ -1,246 +0,0 @@
1
- import Dexie, { Transaction } from 'dexie';
2
-
3
- import { MigrationLLMSettings } from '@/migrations/FromV3ToV4';
4
- import { MigrationAgentChatConfig } from '@/migrations/FromV5ToV6';
5
- import { MigrationKeyValueSettings } from '@/migrations/FromV6ToV7';
6
- import { uuid } from '@/utils/uuid';
7
-
8
- import { DB_File } from '../schemas/files';
9
- import { DB_Message } from '../schemas/message';
10
- import { DB_Plugin } from '../schemas/plugin';
11
- import { DB_Session } from '../schemas/session';
12
- import { DB_SessionGroup } from '../schemas/sessionGroup';
13
- import { DB_Topic } from '../schemas/topic';
14
- import { DB_User } from '../schemas/user';
15
- import { migrateSettingsToUser } from './migrations/migrateSettingsToUser';
16
- import {
17
- dbSchemaV1,
18
- dbSchemaV2,
19
- dbSchemaV3,
20
- dbSchemaV4,
21
- dbSchemaV5,
22
- dbSchemaV6,
23
- dbSchemaV7,
24
- dbSchemaV9,
25
- } from './schemas';
26
- import { DBModel, LOBE_CHAT_LOCAL_DB_NAME } from './types/db';
27
-
28
- export interface LobeDBSchemaMap {
29
- files: DB_File;
30
- messages: DB_Message;
31
- plugins: DB_Plugin;
32
- sessionGroups: DB_SessionGroup;
33
- sessions: DB_Session;
34
- topics: DB_Topic;
35
- users: DB_User;
36
- }
37
-
38
- // Define a local DB
39
- export class BrowserDB extends Dexie {
40
- public files: BrowserDBTable<'files'>;
41
- public sessions: BrowserDBTable<'sessions'>;
42
- public messages: BrowserDBTable<'messages'>;
43
- public topics: BrowserDBTable<'topics'>;
44
- public plugins: BrowserDBTable<'plugins'>;
45
- public sessionGroups: BrowserDBTable<'sessionGroups'>;
46
- public users: BrowserDBTable<'users'>;
47
-
48
- constructor() {
49
- super(LOBE_CHAT_LOCAL_DB_NAME);
50
- this.version(1).stores(dbSchemaV1);
51
- this.version(2).stores(dbSchemaV2);
52
- this.version(3).stores(dbSchemaV3);
53
- this.version(4)
54
- .stores(dbSchemaV4)
55
- .upgrade((trans) => this.upgradeToV4(trans));
56
-
57
- this.version(5)
58
- .stores(dbSchemaV5)
59
- .upgrade((trans) => this.upgradeToV5(trans));
60
-
61
- this.version(6)
62
- .stores(dbSchemaV6)
63
- .upgrade((trans) => this.upgradeToV6(trans));
64
-
65
- this.version(7)
66
- .stores(dbSchemaV7)
67
- .upgrade((trans) => this.upgradeToV7(trans));
68
-
69
- this.version(8)
70
- .stores(dbSchemaV7)
71
- .upgrade((trans) => this.upgradeToV8(trans));
72
-
73
- this.version(9)
74
- .stores(dbSchemaV9)
75
- .upgrade((trans) => this.upgradeToV9(trans));
76
-
77
- this.version(10)
78
- .stores(dbSchemaV9)
79
- .upgrade((trans) => this.upgradeToV10(trans));
80
-
81
- this.version(11)
82
- .stores(dbSchemaV9)
83
- .upgrade((trans) => this.upgradeToV11(trans));
84
-
85
- this.files = this.table('files');
86
- this.sessions = this.table('sessions');
87
- this.messages = this.table('messages');
88
- this.topics = this.table('topics');
89
- this.plugins = this.table('plugins');
90
- this.sessionGroups = this.table('sessionGroups');
91
- this.users = this.table('users');
92
- }
93
-
94
- /**
95
- * 2024.01.22
96
- *
97
- * DB V3 to V4
98
- * from `group = pinned` to `pinned:true`
99
- */
100
- upgradeToV4 = async (trans: Transaction) => {
101
- const sessions = trans.table('sessions');
102
- await sessions.toCollection().modify((session) => {
103
- // translate boolean to number
104
- session.pinned = session.group === 'pinned' ? 1 : 0;
105
- session.group = 'default';
106
- });
107
- };
108
-
109
- /**
110
- * 2024.01.29
111
- * settings from localStorage to indexedDB
112
- */
113
- upgradeToV5 = async (trans: Transaction) => {
114
- const users = trans.table('users');
115
-
116
- // if no user, create one
117
- if ((await users.count()) === 0) {
118
- const data = localStorage.getItem('LOBE_SETTINGS');
119
-
120
- if (data) {
121
- let json;
122
-
123
- try {
124
- json = JSON.parse(data);
125
- } catch {
126
- /* empty */
127
- }
128
-
129
- if (!json?.state?.settings) return;
130
-
131
- const settings = json.state.settings;
132
-
133
- const user = migrateSettingsToUser(settings);
134
- await users.add(user);
135
- }
136
- }
137
- };
138
-
139
- /**
140
- * 2024.02.27
141
- * add uuid to user
142
- */
143
- upgradeToV6 = async (trans: Transaction) => {
144
- const users = trans.table('users');
145
-
146
- await users.toCollection().modify((user: DB_User) => {
147
- if (!user.uuid) user.uuid = uuid();
148
- });
149
- };
150
-
151
- /**
152
- * 2024.03.14
153
- * add `id` in plugins
154
- */
155
- upgradeToV7 = async (trans: Transaction) => {
156
- const plugins = trans.table('plugins');
157
-
158
- await plugins.toCollection().modify((plugin: DB_Plugin) => {
159
- plugin.id = plugin.identifier;
160
- });
161
- };
162
-
163
- upgradeToV8 = async (trans: Transaction) => {
164
- const users = trans.table('users');
165
- await users.toCollection().modify((user: DB_User) => {
166
- if (user.settings) {
167
- user.settings = MigrationLLMSettings.migrateSettings(user.settings as any);
168
- }
169
- });
170
- };
171
-
172
- /**
173
- * 2024.05.11
174
- *
175
- * message role=function to role=tool
176
- */
177
- upgradeToV9 = async (trans: Transaction) => {
178
- const messages = trans.table('messages');
179
- await messages.toCollection().modify(async (message: DBModel<DB_Message>) => {
180
- if ((message.role as string) === 'function') {
181
- const origin = Object.assign({}, message);
182
-
183
- const toolCallId = `tool_call_${message.id}`;
184
- const assistantMessageId = `tool_calls_${message.id}`;
185
-
186
- message.role = 'tool';
187
- message.tool_call_id = toolCallId;
188
- message.parentId = assistantMessageId;
189
-
190
- await messages.add({
191
- ...origin,
192
- content: '',
193
- createdAt: message.createdAt - 10,
194
- error: undefined,
195
- id: assistantMessageId,
196
- role: 'assistant',
197
- tools: [{ ...message.plugin!, id: toolCallId }],
198
- updatedAt: message.updatedAt - 10,
199
- } as DBModel<DB_Message>);
200
- }
201
- });
202
- };
203
-
204
- /**
205
- * 2024.05.25
206
- * migrate some agent config to chatConfig
207
- */
208
- upgradeToV10 = async (trans: Transaction) => {
209
- const sessions = trans.table('sessions');
210
- await sessions.toCollection().modify(async (session: DBModel<DB_Session>) => {
211
- if (session.config)
212
- session.config = MigrationAgentChatConfig.migrateChatConfig(session.config as any);
213
- });
214
- };
215
-
216
- /**
217
- * 2024.05.27
218
- * migrate apiKey in languageModel to keyVaults
219
- */
220
- upgradeToV11 = async (trans: Transaction) => {
221
- const users = trans.table('users');
222
-
223
- await users.toCollection().modify((user: DB_User) => {
224
- if (user.settings) {
225
- user.settings = MigrationKeyValueSettings.migrateSettings(user.settings as any);
226
- }
227
- });
228
- };
229
- }
230
-
231
- export const browserDB = new BrowserDB();
232
-
233
- // ================================================ //
234
- // ================================================ //
235
- // ================================================ //
236
- // ================================================ //
237
- // ================================================ //
238
-
239
- // types helper
240
- export type BrowserDBSchema = {
241
- [t in keyof LobeDBSchemaMap]: {
242
- model: LobeDBSchemaMap[t];
243
- table: Dexie.Table<DBModel<LobeDBSchemaMap[t]>, string>;
244
- };
245
- };
246
- type BrowserDBTable<T extends keyof LobeDBSchemaMap> = BrowserDBSchema[T]['table'];
@@ -1,2 +0,0 @@
1
- export { browserDB } from './db';
2
- export * from './model';