feat(redis): persist dangerous command interception setting

This commit is contained in:
二丫讲梵 authored and GitHub committed 2026-09-14 12:41:01 +08:00
1 parent b28374867a
commit 8efb24f2c7
4 files changed
+29 -5

No files matched your search

+4 -1
View File
@@ -789,7 +789,10 @@ async function resolveActiveExecutableSql(snapshot?: SqlExecutionSnapshot, execu
});
}
const blockDangerousRedisCommands = ref(true);
const blockDangerousRedisCommands = computed({
get: () => settingsStore.editorSettings.blockDangerousRedisCommands,
set: (value: boolean) => settingsStore.updateEditorSettings({ blockDangerousRedisCommands: value }),
});
const databaseRequiredSignal = ref(0);
const databaseRequiredTabId = ref<string | null>(null);
const pendingToolbarExecutionSnapshot = ref<SqlExecutionSnapshot & { tabId?: string }>();
@@ -520,6 +520,8 @@ async function changeCatalog(selectedCatalog: string) {
size="icon"
class="h-6 w-6"
:class="blockDangerousRedisCommands !== false ? 'text-orange-600 bg-orange-100 dark:text-orange-300 dark:bg-orange-900/30' : 'text-muted-foreground/50'"
:aria-label="t('toolbar.blockDangerousRedisCommands')"
:aria-pressed="blockDangerousRedisCommands !== false"
@click="emit('update:blockDangerousRedisCommands', blockDangerousRedisCommands === false)"
>
<Shield class="h-3.5 w-3.5" />
@@ -2,7 +2,7 @@
import { computed, markRaw, nextTick, ref, shallowRef, onMounted, onUnmounted, onActivated, onDeactivated, watch } from "vue";
import type { CalendarDateTime } from "@internationalized/date";
import { useI18n } from "vue-i18n";
import { Search, RefreshCw, Loader2, ChevronRight, ChevronDown, FolderClosed, FolderOpen, Trash2, Plus, KeyRound, TerminalSquare, Asterisk, History, Radio, Clock, Copy, X } from "@lucide/vue";
import { Search, RefreshCw, Loader2, ChevronRight, ChevronDown, FolderClosed, FolderOpen, Trash2, Plus, KeyRound, TerminalSquare, Asterisk, Radio, Clock, Copy, X, Shield } from "@lucide/vue";
import { RecycleScroller } from "vue-virtual-scroller";
import "vue-virtual-scroller/dist/vue-virtual-scroller.css";
import { Splitpanes, Pane } from "splitpanes";
@@ -3470,9 +3470,23 @@ defineExpose({ focusSearch, insertCommand, executeCommand: executeAiCommand });
{{ t("redis.slowlog") }}
</TabsTrigger>
</TabsList>
<Button v-if="activeSidePanel === 'command'" variant="ghost" size="icon" class="h-6 w-6" :title="t('redis.clearHistory')" @click="clearInMemoryHistory">
<History class="size-3.5" />
</Button>
<div v-if="activeSidePanel === 'command'" class="flex shrink-0 items-center gap-1">
<Button
variant="ghost"
size="icon"
class="h-6 w-6"
:class="props.blockDangerousRedisCommands ? 'text-orange-600 bg-orange-100 dark:text-orange-300 dark:bg-orange-900/30' : 'text-muted-foreground/50'"
:aria-label="t('toolbar.blockDangerousRedisCommands')"
:aria-pressed="props.blockDangerousRedisCommands"
:title="t('toolbar.blockDangerousRedisCommands')"
@click="settingsStore.updateEditorSettings({ blockDangerousRedisCommands: !props.blockDangerousRedisCommands })"
>
<Shield class="size-3.5" />
</Button>
<Button variant="ghost" size="icon" class="h-6 w-6" :title="t('redis.clearHistory')" @click="clearInMemoryHistory">
<Trash2 class="size-3.5" />
</Button>
</div>
</div>
<TabsContent value="detail" class="m-0 min-h-0 flex-1 flex flex-col">
+5
View File
@@ -754,6 +754,8 @@ export interface EditorSettings {
executeMode: "all" | "current";
executeModeDefaultVersion: number;
executeAllOnBlankLine: boolean;
/** Whether DBX blocks Redis commands classified as high risk. */
blockDangerousRedisCommands: boolean;
globalConnectTimeoutSecs: number;
connectTimeoutInheritConnectionIds: string[];
globalQueryTimeoutSecs: number;
@@ -995,6 +997,7 @@ export const DEFAULT_EDITOR_SETTINGS: EditorSettings = {
executeMode: "current",
executeModeDefaultVersion: EXECUTE_MODE_CURRENT_DEFAULT_VERSION,
executeAllOnBlankLine: false,
blockDangerousRedisCommands: true,
globalConnectTimeoutSecs: 10,
connectTimeoutInheritConnectionIds: [],
globalQueryTimeoutSecs: DEFAULT_QUERY_TIMEOUT_SECS,
@@ -1450,6 +1453,7 @@ export function normalizeEditorSettings(settings: Partial<EditorSettings>, exist
executeMode: hasCurrentExecuteModeDefault && (settings.executeMode === "all" || settings.executeMode === "current") ? settings.executeMode : DEFAULT_EDITOR_SETTINGS.executeMode,
executeModeDefaultVersion,
executeAllOnBlankLine: settings.executeAllOnBlankLine === true,
blockDangerousRedisCommands: typeof settings.blockDangerousRedisCommands === "boolean" ? settings.blockDangerousRedisCommands : DEFAULT_EDITOR_SETTINGS.blockDangerousRedisCommands,
globalConnectTimeoutSecs: normalizeGlobalConnectTimeoutSecs(settings.globalConnectTimeoutSecs),
connectTimeoutInheritConnectionIds: Array.isArray(settings.connectTimeoutInheritConnectionIds) ? [...new Set(settings.connectTimeoutInheritConnectionIds.filter((id): id is string => typeof id === "string" && id.trim().length > 0).map((id) => id.trim()))] : [],
globalQueryTimeoutSecs: normalizeGlobalQueryTimeoutSecs(settings.globalQueryTimeoutSecs ?? legacyTimeoutSettings.queryTimeoutSecs),
@@ -2200,6 +2204,7 @@ export const useSettingsStore = defineStore("settings", () => {
}
if (partial.executeMode !== undefined) editorSettings.value.executeMode = partial.executeMode;
if (partial.executeAllOnBlankLine !== undefined) editorSettings.value.executeAllOnBlankLine = partial.executeAllOnBlankLine === true;
if (partial.blockDangerousRedisCommands !== undefined) editorSettings.value.blockDangerousRedisCommands = partial.blockDangerousRedisCommands === true;
if (partial.globalConnectTimeoutSecs !== undefined) editorSettings.value.globalConnectTimeoutSecs = normalizeGlobalConnectTimeoutSecs(partial.globalConnectTimeoutSecs);
if (partial.connectTimeoutInheritConnectionIds !== undefined) {
editorSettings.value.connectTimeoutInheritConnectionIds = [...new Set(partial.connectTimeoutInheritConnectionIds.filter((id): id is string => typeof id === "string" && id.trim().length > 0).map((id) => id.trim()))];