From e353fda7a2c398e503b2406a73b2619c9a08536a Mon Sep 17 00:00:00 2001 From: Syngnat Date: Fri, 12 Jun 2026 06:58:41 +0800 Subject: [PATCH] =?UTF-8?q?=E2=99=BB=EF=B8=8F=20refactor(connection):=20?= =?UTF-8?q?=E7=BB=9F=E4=B8=80=E8=BF=9E=E6=8E=A5=E9=A9=B1=E5=8A=A8=E7=B1=BB?= =?UTF-8?q?=E5=9E=8B=E5=BD=92=E4=B8=80=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- frontend/src/components/ConnectionModal.tsx | 47 ++----------------- frontend/src/components/Sidebar.tsx | 11 +---- frontend/src/components/sidebarCoreUtils.ts | 38 ++++----------- .../src/utils/connectionDriverType.test.ts | 43 +++++++++++++++++ frontend/src/utils/connectionDriverType.ts | 47 +++++++++++++++++++ 5 files changed, 104 insertions(+), 82 deletions(-) create mode 100644 frontend/src/utils/connectionDriverType.test.ts create mode 100644 frontend/src/utils/connectionDriverType.ts diff --git a/frontend/src/components/ConnectionModal.tsx b/frontend/src/components/ConnectionModal.tsx index fd52b26..f64cc49 100644 --- a/frontend/src/components/ConnectionModal.tsx +++ b/frontend/src/components/ConnectionModal.tsx @@ -79,6 +79,11 @@ import { supportsSSLClientCertificateForType, supportsSSLForType, } from "../utils/connectionTypeCapabilities"; +import { + normalizeDriverType, + resolveConnectionDriverType, + type DriverStatusSnapshot, +} from "../utils/connectionDriverType"; import { CUSTOM_CONNECTION_DRIVER_HELP } from "../utils/driverImportGuidance"; import { describeUnsupportedOceanBaseProtocol, @@ -246,48 +251,6 @@ const resolveInitialSecretFieldValue = ( } }; -type DriverStatusSnapshot = { - type: string; - name: string; - connectable: boolean; - expectedRevision?: string; - needsUpdate?: boolean; - updateReason?: string; - affectedConnections?: number; - message?: string; -}; - -const normalizeDriverType = (value: string): string => { - const normalized = String(value || "") - .trim() - .toLowerCase(); - if (normalized === "postgresql") return "postgres"; - if (normalized === "elastic") return "elasticsearch"; - if (normalized === "doris") return "diros"; - if ( - normalized === "intersystems" || - normalized === "intersystemsiris" || - normalized === "inter-systems-iris" || - normalized === "inter-systems" - ) - return "iris"; - if ( - normalized === "open_gauss" || - normalized === "open-gauss" || - normalized === "opengauss" - ) - return "opengauss"; - return normalized; -}; - -const resolveConnectionDriverType = (type: string, driver?: string): string => { - const normalizedType = normalizeDriverType(type); - if (normalizedType !== "custom") { - return normalizedType; - } - return normalizeDriverType(driver || ""); -}; - const ConnectionModal: React.FC<{ open: boolean; onClose: () => void; diff --git a/frontend/src/components/Sidebar.tsx b/frontend/src/components/Sidebar.tsx index f9f1ce4..8406197 100644 --- a/frontend/src/components/Sidebar.tsx +++ b/frontend/src/components/Sidebar.tsx @@ -90,6 +90,7 @@ import { buildTableSelectQuery } from '../utils/objectQueryTemplates'; import { getShortcutPlatform, resolveShortcutDisplay } from '../utils/shortcuts'; import { buildExternalSQLDirectoryId, buildExternalSQLRootNode, buildExternalSQLTabId, type ExternalSQLTreeNode } from '../utils/externalSqlTree'; import { SIDEBAR_SQL_EDITOR_DRAG_MIME, encodeSidebarSqlEditorDragPayload } from '../utils/sidebarSqlDrag'; +import type { DriverStatusSnapshot } from '../utils/connectionDriverType'; import JVMModeBadge from './jvm/JVMModeBadge'; import { SEARCH_SCOPE_LABEL_MAP, @@ -237,16 +238,6 @@ interface BatchObjectItem { dataRef: any; } -type DriverStatusSnapshot = { - type: string; - name: string; - connectable: boolean; - expectedRevision?: string; - needsUpdate?: boolean; - updateReason?: string; - message?: string; -}; - const DRIVER_STATUS_CACHE_TTL_MS = 30_000; const SEARCH_SCOPE_ICON_MAP: Record = { diff --git a/frontend/src/components/sidebarCoreUtils.ts b/frontend/src/components/sidebarCoreUtils.ts index 15f9c93..ba8fd9d 100644 --- a/frontend/src/components/sidebarCoreUtils.ts +++ b/frontend/src/components/sidebarCoreUtils.ts @@ -1,5 +1,10 @@ import type React from 'react'; import type { SavedConnection } from '../types'; +import { + isPostgresSchemaDialect as resolveIsPostgresSchemaDialect, + normalizeDriverType as normalizeConnectionDriverType, + resolveSavedConnectionDriverType as resolveSavedConnectionDriverTypeBase, +} from '../utils/connectionDriverType'; const SIDEBAR_CONTEXT_MENU_SAFE_GAP = 8; export const SIDEBAR_CONTEXT_MENU_FALLBACK_WIDTH = 264; @@ -79,36 +84,9 @@ export const isConnectionTreeKey = (key: React.Key, connectionId: string): boole return text === connectionId || text.startsWith(`${connectionId}-`); }; -export const normalizeDriverType = (value: string): string => { - const normalized = String(value || '').trim().toLowerCase(); - if (normalized === 'postgresql' || normalized === 'pg' || normalized === 'pq' || normalized === 'pgx') return 'postgres'; - if (normalized === 'elastic') return 'elasticsearch'; - if (normalized === 'doris') return 'diros'; - if ( - normalized === 'open_gauss' || - normalized === 'open-gauss' || - normalized === 'opengauss' - ) return 'opengauss'; - if ( - normalized === 'intersystems' || - normalized === 'intersystemsiris' || - normalized === 'inter-systems' || - normalized === 'inter-systems-iris' - ) return 'iris'; - return normalized; -}; - -export const resolveSavedConnectionDriverType = (conn: SavedConnection | undefined): string => { - const type = normalizeDriverType(conn?.config?.type || ''); - if (type !== 'custom') { - return type; - } - return normalizeDriverType(conn?.config?.driver || ''); -}; - -export const isPostgresSchemaDialect = (dialect: string): boolean => ( - ['postgres', 'kingbase', 'highgo', 'vastbase', 'opengauss'].includes(normalizeDriverType(dialect)) -); +export const normalizeDriverType = normalizeConnectionDriverType; +export const resolveSavedConnectionDriverType = resolveSavedConnectionDriverTypeBase; +export const isPostgresSchemaDialect = resolveIsPostgresSchemaDialect; export const SEARCH_SCOPE_OPTIONS: Array<{ value: SearchScope; label: string }> = [ { value: 'smart', label: '智能' }, diff --git a/frontend/src/utils/connectionDriverType.test.ts b/frontend/src/utils/connectionDriverType.test.ts new file mode 100644 index 0000000..1d9230d --- /dev/null +++ b/frontend/src/utils/connectionDriverType.test.ts @@ -0,0 +1,43 @@ +import { describe, expect, it } from 'vitest'; + +import { + isPostgresSchemaDialect, + normalizeDriverType, + resolveConnectionDriverType, + resolveSavedConnectionDriverType, +} from './connectionDriverType'; + +describe('connectionDriverType', () => { + it('normalizes built-in driver aliases shared by connection modal and sidebar', () => { + expect(normalizeDriverType('postgresql')).toBe('postgres'); + expect(normalizeDriverType('pgx')).toBe('postgres'); + expect(normalizeDriverType('elastic')).toBe('elasticsearch'); + expect(normalizeDriverType('doris')).toBe('diros'); + expect(normalizeDriverType('open-gauss')).toBe('opengauss'); + expect(normalizeDriverType('InterSystemsIRIS')).toBe('iris'); + }); + + it('resolves custom connection driver types from the selected driver field', () => { + expect(resolveConnectionDriverType('mysql', 'postgresql')).toBe('mysql'); + expect(resolveConnectionDriverType('custom', 'postgresql')).toBe('postgres'); + expect(resolveConnectionDriverType('custom', 'open_gauss')).toBe('opengauss'); + expect(resolveConnectionDriverType('custom', '')).toBe(''); + }); + + it('resolves saved custom connections using the same driver aliases', () => { + const conn = { + config: { + type: 'custom', + driver: 'pg', + }, + } as any; + expect(resolveSavedConnectionDriverType(conn)).toBe('postgres'); + }); + + it('detects postgres-compatible schema dialects', () => { + expect(isPostgresSchemaDialect('postgres')).toBe(true); + expect(isPostgresSchemaDialect('kingbase')).toBe(true); + expect(isPostgresSchemaDialect('open-gauss')).toBe(true); + expect(isPostgresSchemaDialect('mysql')).toBe(false); + }); +}); diff --git a/frontend/src/utils/connectionDriverType.ts b/frontend/src/utils/connectionDriverType.ts new file mode 100644 index 0000000..0753a2e --- /dev/null +++ b/frontend/src/utils/connectionDriverType.ts @@ -0,0 +1,47 @@ +import type { SavedConnection } from '../types'; + +export type DriverStatusSnapshot = { + type: string; + name: string; + connectable: boolean; + expectedRevision?: string; + needsUpdate?: boolean; + updateReason?: string; + affectedConnections?: number; + message?: string; +}; + +export const normalizeDriverType = (value: string): string => { + const normalized = String(value || '').trim().toLowerCase(); + if (normalized === 'postgresql' || normalized === 'pg' || normalized === 'pq' || normalized === 'pgx') return 'postgres'; + if (normalized === 'elastic') return 'elasticsearch'; + if (normalized === 'doris') return 'diros'; + if ( + normalized === 'open_gauss' || + normalized === 'open-gauss' || + normalized === 'opengauss' + ) return 'opengauss'; + if ( + normalized === 'intersystems' || + normalized === 'intersystemsiris' || + normalized === 'inter-systems' || + normalized === 'inter-systems-iris' + ) return 'iris'; + return normalized; +}; + +export const resolveConnectionDriverType = (type: string, driver?: string): string => { + const normalizedType = normalizeDriverType(type); + if (normalizedType !== 'custom') { + return normalizedType; + } + return normalizeDriverType(driver || ''); +}; + +export const resolveSavedConnectionDriverType = (conn: SavedConnection | undefined): string => { + return resolveConnectionDriverType(conn?.config?.type || '', conn?.config?.driver || ''); +}; + +export const isPostgresSchemaDialect = (dialect: string): boolean => ( + ['postgres', 'kingbase', 'highgo', 'vastbase', 'opengauss'].includes(normalizeDriverType(dialect)) +);