mirror of
https://github.com/Syngnat/GoNavi.git
synced 2026-06-23 06:53:52 +08:00
♻️ refactor(sidebar): 迁出命令搜索相关类型与 shouldLoadSidebarNodeOnExpand
- 迁出 V2CommandSearchMode/V2CommandSearchQuery 类型与 parseV2CommandSearchQuery(支持 @/?前缀切换 object/ai 模式) - 迁出 shouldLoadSidebarNodeOnExpand(节点懒加载判定) - SidebarNodeLike 加可选 key 字段以适配测试用法 - Sidebar.tsx 从 10235 减至 10187 行,sidebarHelpers.ts 增至 215 行
This commit is contained in:
@@ -4,11 +4,15 @@ import {
|
||||
formatSidebarRowCount,
|
||||
hasSidebarLazyChildren,
|
||||
shouldClearSidebarActiveContextOnEmptySelect,
|
||||
shouldLoadSidebarNodeOnExpand,
|
||||
getV2RailConnectionGroupBadgeText,
|
||||
isV2SidebarObjectNode,
|
||||
resolveV2ObjectGroupTitle,
|
||||
resolveSidebarTableNameForCopy,
|
||||
parseV2CommandSearchQuery,
|
||||
type V2ExplorerFilter,
|
||||
type V2CommandSearchMode,
|
||||
type V2CommandSearchQuery,
|
||||
} from './sidebar/sidebarHelpers';
|
||||
// 重新导出,保持外部测试文件的 `from './Sidebar'` 兼容
|
||||
export {
|
||||
@@ -16,10 +20,12 @@ export {
|
||||
formatSidebarRowCount,
|
||||
hasSidebarLazyChildren,
|
||||
shouldClearSidebarActiveContextOnEmptySelect,
|
||||
shouldLoadSidebarNodeOnExpand,
|
||||
getV2RailConnectionGroupBadgeText,
|
||||
isV2SidebarObjectNode,
|
||||
resolveV2ObjectGroupTitle,
|
||||
resolveSidebarTableNameForCopy,
|
||||
parseV2CommandSearchQuery,
|
||||
} from './sidebar/sidebarHelpers';
|
||||
import React, { useEffect, useState, useMemo, useRef, useCallback, useDeferredValue } from 'react';
|
||||
import { createPortal } from 'react-dom';
|
||||
@@ -290,17 +296,7 @@ export const SQLFileExecutionProgressContent: React.FC<SQLFileExecutionProgressS
|
||||
</>
|
||||
);
|
||||
|
||||
export const shouldLoadSidebarNodeOnExpand = (
|
||||
node: Pick<TreeNode, 'type' | 'children' | 'isLeaf'> | null | undefined,
|
||||
): boolean => {
|
||||
if (!node || node.isLeaf === true || hasSidebarLazyChildren(node.children)) return false;
|
||||
return node.type === 'connection'
|
||||
|| node.type === 'database'
|
||||
|| node.type === 'external-sql-root'
|
||||
|| node.type === 'table'
|
||||
|| node.type === 'jvm-mode'
|
||||
|| node.type === 'jvm-resource';
|
||||
};
|
||||
// shouldLoadSidebarNodeOnExpand 已迁移到 ./sidebar/sidebarHelpers
|
||||
|
||||
// resolveSidebarTableNameForCopy 已迁移到 ./sidebar/sidebarHelpers
|
||||
|
||||
@@ -597,51 +593,7 @@ export type V2CommandSearchItem =
|
||||
dbName?: string;
|
||||
};
|
||||
|
||||
export type V2CommandSearchMode = 'default' | 'object' | 'ai';
|
||||
|
||||
export interface V2CommandSearchQuery {
|
||||
mode: V2CommandSearchMode;
|
||||
rawValue: string;
|
||||
keyword: string;
|
||||
normalizedKeyword: string;
|
||||
aiPrompt: string;
|
||||
}
|
||||
|
||||
export const parseV2CommandSearchQuery = (value: unknown): V2CommandSearchQuery => {
|
||||
const rawValue = String(value ?? '');
|
||||
const trimmedValue = rawValue.trim();
|
||||
const firstChar = trimmedValue.charAt(0);
|
||||
|
||||
if (firstChar === '@' || firstChar === '@') {
|
||||
const keyword = trimmedValue.slice(1).trim();
|
||||
return {
|
||||
mode: 'object',
|
||||
rawValue,
|
||||
keyword,
|
||||
normalizedKeyword: keyword.toLowerCase(),
|
||||
aiPrompt: '',
|
||||
};
|
||||
}
|
||||
|
||||
if (firstChar === '?' || firstChar === '?') {
|
||||
const aiPrompt = trimmedValue.slice(1).trim();
|
||||
return {
|
||||
mode: 'ai',
|
||||
rawValue,
|
||||
keyword: aiPrompt,
|
||||
normalizedKeyword: aiPrompt.toLowerCase(),
|
||||
aiPrompt,
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
mode: 'default',
|
||||
rawValue,
|
||||
keyword: trimmedValue,
|
||||
normalizedKeyword: trimmedValue.toLowerCase(),
|
||||
aiPrompt: '',
|
||||
};
|
||||
};
|
||||
// V2CommandSearchMode / V2CommandSearchQuery / parseV2CommandSearchQuery 已迁移到 ./sidebar/sidebarHelpers
|
||||
|
||||
export const resolveSidebarConnectionIdFromKey = (
|
||||
key: unknown,
|
||||
|
||||
@@ -106,6 +106,7 @@ export const isV2SidebarObjectNode = (
|
||||
* 让 sidebarHelpers 不依赖 Sidebar.tsx 内部的 TreeNode 定义,避免循环依赖。
|
||||
*/
|
||||
export interface SidebarNodeLike {
|
||||
key?: string;
|
||||
type?: string;
|
||||
dataRef?: any;
|
||||
title?: string;
|
||||
@@ -140,3 +141,75 @@ export const resolveSidebarTableNameForCopy = (
|
||||
): string => {
|
||||
return String(node?.dataRef?.tableName || node?.dataRef?.viewName || node?.dataRef?.eventName || node?.title || '').trim();
|
||||
};
|
||||
|
||||
// === 命令搜索相关类型与解析(V2 Command Search)===
|
||||
|
||||
/** 命令搜索模式:default(默认)/ object(@前缀,对象搜索)/ ai(?或?前缀,AI 提问) */
|
||||
export type V2CommandSearchMode = 'default' | 'object' | 'ai';
|
||||
|
||||
/** 命令搜索查询解析结果 */
|
||||
export interface V2CommandSearchQuery {
|
||||
mode: V2CommandSearchMode;
|
||||
rawValue: string;
|
||||
keyword: string;
|
||||
normalizedKeyword: string;
|
||||
aiPrompt: string;
|
||||
}
|
||||
|
||||
/**
|
||||
* parseV2CommandSearchQuery 解析命令搜索框的输入。
|
||||
* - "@" 或 "@" 前缀:对象搜索模式
|
||||
* - "?" 或 "?" 前缀:AI 提问模式
|
||||
* - 无前缀:默认模式
|
||||
*/
|
||||
export const parseV2CommandSearchQuery = (value: unknown): V2CommandSearchQuery => {
|
||||
const rawValue = String(value ?? '');
|
||||
const trimmedValue = rawValue.trim();
|
||||
const firstChar = trimmedValue.charAt(0);
|
||||
|
||||
if (firstChar === '@' || firstChar === '@') {
|
||||
const keyword = trimmedValue.slice(1).trim();
|
||||
return {
|
||||
mode: 'object',
|
||||
rawValue,
|
||||
keyword,
|
||||
normalizedKeyword: keyword.toLowerCase(),
|
||||
aiPrompt: '',
|
||||
};
|
||||
}
|
||||
|
||||
if (firstChar === '?' || firstChar === '?') {
|
||||
const aiPrompt = trimmedValue.slice(1).trim();
|
||||
return {
|
||||
mode: 'ai',
|
||||
rawValue,
|
||||
keyword: aiPrompt,
|
||||
normalizedKeyword: aiPrompt.toLowerCase(),
|
||||
aiPrompt,
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
mode: 'default',
|
||||
rawValue,
|
||||
keyword: trimmedValue,
|
||||
normalizedKeyword: trimmedValue.toLowerCase(),
|
||||
aiPrompt: '',
|
||||
};
|
||||
};
|
||||
|
||||
/**
|
||||
* shouldLoadSidebarNodeOnExpand 判断节点展开时是否需要懒加载子节点。
|
||||
* 仅 connection/database/external-sql-root/table/jvm-mode/jvm-resource 类型且无已加载 children 时返回 true。
|
||||
*/
|
||||
export const shouldLoadSidebarNodeOnExpand = (
|
||||
node: Pick<SidebarNodeLike, 'type' | 'children' | 'isLeaf'> | null | undefined,
|
||||
): boolean => {
|
||||
if (!node || node.isLeaf === true || hasSidebarLazyChildren(node.children)) return false;
|
||||
return node.type === 'connection'
|
||||
|| node.type === 'database'
|
||||
|| node.type === 'external-sql-root'
|
||||
|| node.type === 'table'
|
||||
|| node.type === 'jvm-mode'
|
||||
|| node.type === 'jvm-resource';
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user