diff --git a/frontend/src/components/QueryEditor.tsx b/frontend/src/components/QueryEditor.tsx index 2664901..79292bd 100644 --- a/frontend/src/components/QueryEditor.tsx +++ b/frontend/src/components/QueryEditor.tsx @@ -2211,9 +2211,8 @@ const QueryEditor: React.FC<{ tab: TabData; isActive?: boolean }> = ({ tab, isAc const [saveModalMode, setSaveModalMode] = useState<'save' | 'rename'>('save'); const [saveForm] = Form.useForm(); - // SQL 诊断工作台:Ctrl+Shift+D 触发(Mac 为 Cmd+Shift+D) + // SQL 诊断工作台与慢 SQL 历史:通过快捷键管理系统注册(避免与 toggleTheme/toggleLogPanel 冲突) const [explainOpen, setExplainOpen] = useState(false); - // 慢 SQL 历史:Ctrl+Shift+H 触发 const [slowQueryOpen, setSlowQueryOpen] = useState(false); // Database Selection @@ -2275,23 +2274,6 @@ const QueryEditor: React.FC<{ tab: TabData; isActive?: boolean }> = ({ tab, isAc } as any; }, [connections, currentConnectionId]); - useEffect(() => { - if (!isActive) return; - const handler = (e: KeyboardEvent) => { - if (!(e.ctrlKey || e.metaKey) || !e.shiftKey) return; - const key = e.key.toLowerCase(); - if (key === 'd') { - e.preventDefault(); - setExplainOpen(true); - } else if (key === 'h') { - e.preventDefault(); - setSlowQueryOpen(true); - } - }; - window.addEventListener('keydown', handler); - return () => window.removeEventListener('keydown', handler); - }, [isActive]); - const addSqlLog = useStore(state => state.addSqlLog); const addTab = useStore(state => state.addTab); const setActiveContext = useStore(state => state.setActiveContext); @@ -2323,6 +2305,33 @@ const QueryEditor: React.FC<{ tab: TabData; isActive?: boolean }> = ({ tab, isAc () => resolveShortcutBinding(shortcutOptions, 'runQuery', activeShortcutPlatform), [activeShortcutPlatform, shortcutOptions], ); + // SQL 诊断 / 慢 SQL 历史的快捷键绑定(从 store 读取,用户可在快捷键管理面板自定义) + const diagnoseQueryShortcutBinding = useMemo( + () => resolveShortcutBinding(shortcutOptions, 'diagnoseQuery', activeShortcutPlatform), + [activeShortcutPlatform, shortcutOptions], + ); + const showSlowQueriesShortcutBinding = useMemo( + () => resolveShortcutBinding(shortcutOptions, 'showSlowQueries', activeShortcutPlatform), + [activeShortcutPlatform, shortcutOptions], + ); + + // SQL 诊断 / 慢 SQL 历史的快捷键监听(必须在 binding 声明之后) + useEffect(() => { + if (!isActive) return; + const handler = (e: KeyboardEvent) => { + if (diagnoseQueryShortcutBinding?.enabled && isShortcutMatch(e, diagnoseQueryShortcutBinding.combo)) { + e.preventDefault(); + setExplainOpen(true); + return; + } + if (showSlowQueriesShortcutBinding?.enabled && isShortcutMatch(e, showSlowQueriesShortcutBinding.combo)) { + e.preventDefault(); + setSlowQueryOpen(true); + } + }; + window.addEventListener('keydown', handler); + return () => window.removeEventListener('keydown', handler); + }, [isActive, diagnoseQueryShortcutBinding, showSlowQueriesShortcutBinding]); const selectCurrentStatementShortcutBinding = useMemo( () => resolveShortcutBinding(shortcutOptions, 'selectCurrentStatement', activeShortcutPlatform), [activeShortcutPlatform, shortcutOptions], @@ -5840,6 +5849,35 @@ const QueryEditor: React.FC<{ tab: TabData; isActive?: boolean }> = ({ tab, isAc label: translate('query_editor.action.export_sql_file'), onClick: () => void handleExportSQLFile(), }, + { type: 'divider' }, + { + key: 'diagnose-query', + label: ( + + {translate('app.shortcuts.action.diagnoseQuery.label' as any) || 'SQL 诊断'} + {diagnoseQueryShortcutBinding?.enabled && diagnoseQueryShortcutBinding.combo && ( + + {getShortcutDisplayLabel(diagnoseQueryShortcutBinding.combo, activeShortcutPlatform)} + + )} + + ), + onClick: () => setExplainOpen(true), + }, + { + key: 'show-slow-queries', + label: ( + + {translate('app.shortcuts.action.showSlowQueries.label' as any) || '慢 SQL 历史'} + {showSlowQueriesShortcutBinding?.enabled && showSlowQueriesShortcutBinding.combo && ( + + {getShortcutDisplayLabel(showSlowQueriesShortcutBinding.combo, activeShortcutPlatform)} + + )} + + ), + onClick: () => setSlowQueryOpen(true), + }, ]; useEffect(() => { diff --git a/frontend/src/utils/shortcuts.ts b/frontend/src/utils/shortcuts.ts index ed2555a..2dc500d 100644 --- a/frontend/src/utils/shortcuts.ts +++ b/frontend/src/utils/shortcuts.ts @@ -18,7 +18,9 @@ export type ShortcutAction = | 'toggleTheme' | 'openShortcutManager' | 'toggleMacFullscreen' - | 'resetWindowZoom'; + | 'resetWindowZoom' + | 'diagnoseQuery' + | 'showSlowQueries'; export type ShortcutPlatform = 'mac' | 'windows'; @@ -111,6 +113,8 @@ export const SHORTCUT_ACTION_ORDER: ShortcutAction[] = [ 'toggleAIPanel', 'toggleLogPanel', 'toggleTheme', + 'diagnoseQuery', + 'showSlowQueries', 'openShortcutManager', 'toggleMacFullscreen', 'resetWindowZoom', @@ -202,6 +206,18 @@ const SHORTCUT_ACTION_META_DEFINITIONS: Record