-
Notifications
You must be signed in to change notification settings - Fork 625
fix: realign prompt editor styling #1006
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fix: realign prompt editor styling #1006
Conversation
WalkthroughReplaces large inline settings and prompt UI blocks with multiple focused Vue components, delegating state and behaviors (search engines, proxy, logging, web content limit, search assistant model, prompt CRUD/import/export, editor sheets, and toggle rows) into dedicated components and adding i18n keys for character units. Changes
Sequence Diagram(s)sequenceDiagram
autonumber
actor U as User
participant CS as CommonSettings.vue
participant SES as SearchEngineSettingsSection
participant CFG as configPresenter
participant ST as settingsStore
U->>CS: Open Common Settings
CS->>SES: render SearchEngineSettingsSection
U->>SES: Add custom engine (name, url)
SES->>SES: validate url contains "{query}"
SES->>CFG: persist custom engine
SES->>ST: refresh engine list
SES-->>U: select new engine
sequenceDiagram
autonumber
actor U as User
participant PXY as ProxySettingsSection
participant CFG as configPresenter
Note over PXY: on mount -> load mode + url
U->>PXY: Change proxy mode
PXY->>CFG: setProxyMode(mode)
alt mode == custom
U->>PXY: Enter URL
PXY->>PXY: debounce -> validate URL
alt valid
PXY->>CFG: setCustomProxyUrl(url)
PXY-->>U: show persisted state
else invalid
PXY-->>U: show error
end
end
sequenceDiagram
autonumber
actor U as User
participant H as PromptSettingsHeader
participant PS as PromptSetting.vue
participant CPS as CustomPromptSettingsSection
participant Store as promptsStore
U->>H: Click Import
H->>PS: emit(import)
PS->>CPS: customPromptSection.value?.importPrompts()
CPS->>U: open file picker
CPS->>CPS: validate & merge JSON
CPS->>Store: savePrompts(merged)
CPS-->>U: toast success/error
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45–90 minutes Possibly related PRs
Poem
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 12
🧹 Nitpick comments (7)
src/renderer/settings/components/prompt/SystemPromptEditorSheet.vue (1)
129-160: Consider consolidating duplicate form reset logic.The form reset logic is duplicated across two watchers. Both handle the same cases: reset when closed/no prompt, or populate from prompt.
Consider extracting the common logic:
+const applyPrompt = (prompt: SystemPromptForm | null) => { + if (!prompt) { + resetForm() + return + } + form.id = prompt.id + form.name = prompt.name + form.content = prompt.content +} + watch( () => props.open, (open) => { if (!open) { resetForm() return } - - if (props.prompt) { - form.id = props.prompt.id - form.name = props.prompt.name - form.content = props.prompt.content - } else { - resetForm() - } + applyPrompt(props.prompt) } ) watch( () => props.prompt, (prompt) => { if (!props.open) return - - if (prompt) { - form.id = prompt.id - form.name = prompt.name - form.content = prompt.content - } else { - resetForm() - } + applyPrompt(prompt) } )src/renderer/settings/components/prompt/PromptEditorSheet.vue (1)
458-464: Consider extracting file size formatter to shared utility.This helper function could be reused across the codebase wherever file sizes are displayed.
Extract to a shared utility file (e.g.,
src/renderer/lib/utils.tsorsrc/renderer/utils/format.ts):export const formatFileSize = (bytes: number): string => { if (bytes === 0) return '0 Bytes' const k = 1024 const sizes = ['Bytes', 'KB', 'MB', 'GB'] const i = Math.floor(Math.log(bytes) / Math.log(k)) return `${parseFloat((bytes / Math.pow(k, i)).toFixed(2))} ${sizes[i]}` }Then import and use it:
import { formatFileSize } from '@/lib/utils'src/renderer/settings/components/common/ProxySettingsSection.vue (1)
74-74: Consider using more precise timer type.The timer type
number | nullworks in browsers butReturnType<typeof setTimeout>is more portable across environments.Apply this diff:
-let proxyUrlDebounceTimer: number | null = null +let proxyUrlDebounceTimer: ReturnType<typeof setTimeout> | null = nullsrc/renderer/settings/components/common/SettingToggleRow.vue (1)
24-24: Remove unnecessarytoRefs.In
<script setup>, props are already reactive. ThetoRefscall creates unnecessary refs that aren't used elsewhere.Remove the unused destructured refs:
const props = defineProps<{ id: string; icon: string; label: string; modelValue: boolean }>() const emit = defineEmits<{ (e: 'update:modelValue', value: boolean): void }>() const langStore = useLanguageStore() - -const { id, icon, label, modelValue } = toRefs(props)Then update template references to use
props.prefix:- <Icon :icon="icon" class="w-4 h-4 text-muted-foreground" /> - <span class="truncate">{{ label }}</span> + <Icon :icon="props.icon" class="w-4 h-4 text-muted-foreground" /> + <span class="truncate">{{ props.label }}</span>- <Switch :id="id" :model-value="modelValue" @update:model-value="emit('update:modelValue', $event)" /> + <Switch :id="props.id" :model-value="props.modelValue" @update:model-value="emit('update:modelValue', $event)" />src/renderer/settings/components/prompt/SystemPromptSettingsSection.vue (3)
138-146: Consider adding user feedback for load failures.The
loadSystemPromptsmethod catches errors but only logs them to the console. Users won't be aware if system prompts fail to load on mount. Consider showing a toast notification to inform users of the failure.Apply this diff to add user feedback:
const loadSystemPrompts = async () => { try { systemPrompts.value = await settingsStore.getSystemPrompts() selectedSystemPromptId.value = await settingsStore.getDefaultSystemPromptId() updateCurrentSystemPrompt() } catch (error) { console.error('Failed to load system prompts:', error) + toast({ + title: t('promptSetting.systemPromptLoadFailed'), + variant: 'destructive' + }) } }
167-195: Potential state inconsistency with optimistic updates.The method performs optimistic updates to the local array (lines 176-182) after calling
updateSystemPrompt. If the store update succeeds but the local array update encounters an issue (e.g., index not found due to race condition), the UI state could diverge from the store state. Since you're showing a success toast immediately after the store update, consider either:
- Removing the manual array update and relying on a reload (simpler, consistent)
- Performing the local update before the store call (true optimistic) and reverting on error
Solution 1 (simpler approach):
const saveCurrentSystemPrompt = async () => { if (!currentSystemPrompt.value) return try { await settingsStore.updateSystemPrompt(currentSystemPrompt.value.id, { content: currentSystemPrompt.value.content, updatedAt: Date.now() }) - const index = systemPrompts.value.findIndex( - (prompt) => prompt.id === currentSystemPrompt.value!.id - ) - if (index !== -1) { - systemPrompts.value[index].content = currentSystemPrompt.value.content - systemPrompts.value[index].updatedAt = Date.now() - } + await loadSystemPrompts() toast({ title: t('promptSetting.systemPromptUpdated'), variant: 'default' }) } catch (error) { console.error('Failed to save system prompt:', error) toast({ title: t('promptSetting.systemPromptSaveFailed'), variant: 'destructive' }) } }
197-230: Extract hardcoded default prompt to a constant.The default system prompt content (lines 199-202) is a long multi-line string embedded in the method. For better maintainability and potential reuse, consider extracting this to a module-level constant.
Apply this diff:
+const DEFAULT_SYSTEM_PROMPT_CONTENT = `You are DeepChat, a highly capable AI assistant. Your goal is to fully complete the user's requested task before handing the conversation back to them. Keep working autonomously until the task is fully resolved. +Be thorough in gathering information. Before replying, make sure you have all the details necessary to provide a complete solution. Use additional tools or ask clarifying questions when needed, but if you can find the answer on your own, avoid asking the user for help. +When using tools, briefly describe your intended steps first—for example, which tool you'll use and for what purpose. +Adhere to this in all languages.Always respond in the same language as the user's query.` + const { t } = useI18n() const { toast } = useToast() const settingsStore = useSettingsStore()Then update the method:
const resetDefaultSystemPrompt = async () => { try { - const originalContent = `You are DeepChat, a highly capable AI assistant. Your goal is to fully complete the user's requested task before handing the conversation back to them. Keep working autonomously until the task is fully resolved. -Be thorough in gathering information. Before replying, make sure you have all the details necessary to provide a complete solution. Use additional tools or ask clarifying questions when needed, but if you can find the answer on your own, avoid asking the user for help. -When using tools, briefly describe your intended steps first—for example, which tool you'll use and for what purpose. -Adhere to this in all languages.Always respond in the same language as the user's query.` - - await settingsStore.updateSystemPrompt('default', { - content: originalContent, + await settingsStore.updateSystemPrompt('default', { + content: DEFAULT_SYSTEM_PROMPT_CONTENT, updatedAt: Date.now() }) if (currentSystemPrompt.value && currentSystemPrompt.value.id === 'default') { - currentSystemPrompt.value.content = originalContent + currentSystemPrompt.value.content = DEFAULT_SYSTEM_PROMPT_CONTENT } const index = systemPrompts.value.findIndex((prompt) => prompt.id === 'default') if (index !== -1) { - systemPrompts.value[index].content = originalContent + systemPrompts.value[index].content = DEFAULT_SYSTEM_PROMPT_CONTENT systemPrompts.value[index].updatedAt = Date.now() }
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (13)
src/renderer/settings/components/CommonSettings.vue(1 hunks)src/renderer/settings/components/PromptSetting.vue(1 hunks)src/renderer/settings/components/common/LoggingSettingsSection.vue(1 hunks)src/renderer/settings/components/common/ProxySettingsSection.vue(1 hunks)src/renderer/settings/components/common/SearchAssistantModelSection.vue(1 hunks)src/renderer/settings/components/common/SearchEngineSettingsSection.vue(1 hunks)src/renderer/settings/components/common/SettingToggleRow.vue(1 hunks)src/renderer/settings/components/common/WebContentLimitSetting.vue(1 hunks)src/renderer/settings/components/prompt/CustomPromptSettingsSection.vue(1 hunks)src/renderer/settings/components/prompt/PromptEditorSheet.vue(1 hunks)src/renderer/settings/components/prompt/PromptSettingsHeader.vue(1 hunks)src/renderer/settings/components/prompt/SystemPromptEditorSheet.vue(1 hunks)src/renderer/settings/components/prompt/SystemPromptSettingsSection.vue(1 hunks)
🧰 Additional context used
📓 Path-based instructions (9)
src/renderer/**/*.{vue,ts,js,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/project-structure.mdc)
渲染进程代码放在
src/renderer
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
src/renderer/**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,tsx,vue}: Use descriptive variable names with auxiliary verbs (e.g., isLoading, hasError).
Use TypeScript for all code; prefer types over interfaces.
Avoid enums; use const objects instead.
Use arrow functions for methods and computed properties.
Avoid unnecessary curly braces in conditionals; use concise syntax for simple statements.
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
src/renderer/**/*.{vue,ts}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
Implement lazy loading for routes and components.
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
src/renderer/**/*.{ts,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,vue}: Use useFetch and useAsyncData for data fetching.
Implement SEO best practices using Nuxt's useHead and useSeoMeta.Use Pinia for frontend state management (do not introduce alternative state libraries)
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
**/*.{ts,tsx,js,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Use English for all logs and comments
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Enable and adhere to strict TypeScript typing (avoid implicit any, prefer precise types)
Use PascalCase for TypeScript types and classes
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
**/*.{ts,tsx,js,jsx,vue,css,scss,md,json,yml,yaml}
📄 CodeRabbit inference engine (AGENTS.md)
Prettier style: single quotes, no semicolons, print width 100; run pnpm run format
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (AGENTS.md)
**/*.{ts,tsx,js,jsx,vue}: Use OxLint for JS/TS code; keep lint clean
Use camelCase for variables and functions
Use SCREAMING_SNAKE_CASE for constants
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
src/renderer/**/*.vue
📄 CodeRabbit inference engine (AGENTS.md)
Name Vue component files in PascalCase (e.g., ChatInput.vue)
Files:
src/renderer/settings/components/prompt/PromptSettingsHeader.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vuesrc/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/prompt/SystemPromptSettingsSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vuesrc/renderer/settings/components/prompt/CustomPromptSettingsSection.vuesrc/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/prompt/SystemPromptEditorSheet.vuesrc/renderer/settings/components/PromptSetting.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vue
🪛 GitHub Actions: PR Check
src/renderer/settings/components/common/LoggingSettingsSection.vue
[warning] 1-1: Prettier formatting check failed. Run 'prettier --write' to fix code style issues in this file.
src/renderer/settings/components/common/WebContentLimitSetting.vue
[warning] 1-1: Prettier formatting check failed. Run 'prettier --write' to fix code style issues in this file.
src/renderer/settings/components/common/ProxySettingsSection.vue
[warning] 1-1: Prettier formatting check failed. Run 'prettier --write' to fix code style issues in this file.
src/renderer/settings/components/common/SearchEngineSettingsSection.vue
[warning] 1-1: Prettier formatting check failed. Run 'prettier --write' to fix code style issues in this file.
src/renderer/settings/components/common/SettingToggleRow.vue
[warning] 1-1: Prettier formatting check failed. Run 'prettier --write' to fix code style issues in this file.
src/renderer/settings/components/common/SearchAssistantModelSection.vue
[warning] 1-1: Prettier formatting check failed. Run 'prettier --write' to fix code style issues in this file.
🔇 Additional comments (9)
src/renderer/settings/components/prompt/PromptEditorSheet.vue (2)
48-57: LGTM: Checkbox boolean coercion.The pattern
@update:checked="(value) => (form.enabled = value === true)"correctly coerces the checkbox value to a boolean, aligning with the PR objectives.
68-72: LGTM: Textarea styling matches PR objectives.The textarea correctly applies
font-mono resize-yclasses for a monospace, resizable content area as specified in the PR description.src/renderer/settings/components/prompt/PromptSettingsHeader.vue (1)
1-28: LGTM: Clean event-driven header component.The component follows a simple, focused design pattern with proper event emissions and i18n support.
src/renderer/settings/components/common/LoggingSettingsSection.vue (2)
77-93: LGTM: Dialog confirmation pattern.The implementation correctly uses a confirmation dialog before applying the logging setting change, which is appropriate given the restart requirement.
1-94: Fix Prettier formatting errors
Runpnpm run format src/renderer/settings/components/common/LoggingSettingsSection.vuelocally and commit the updated file.src/renderer/settings/components/common/SettingToggleRow.vue (1)
1-25: Fix Prettier formatting
Runpnpm exec prettier --write src/renderer/settings/components/common/SettingToggleRow.vueand commit the resulting changes.src/renderer/settings/components/common/SearchAssistantModelSection.vue (1)
1-58: Fix Prettier formatting in SearchAssistantModelSection.vue
Runpnpm exec prettier --write src/renderer/settings/components/common/SearchAssistantModelSection.vue(orpnpm run format) and re-run CI.src/renderer/settings/components/common/WebContentLimitSetting.vue (1)
1-136: Run Prettier to fix formattingThe file fails the Prettier check. Execute:
npx prettier --write src/renderer/settings/components/common/WebContentLimitSetting.vuesrc/renderer/settings/components/common/ProxySettingsSection.vue (1)
1-114: Ensure Prettier is installed and format the file
The CI reports a formatting failure. Runpnpm installto install dependencies, then:pnpm run format src/renderer/settings/components/common/ProxySettingsSection.vue
| try { | ||
| let customSearchEngines: SearchEngineTemplate[] = [] | ||
| try { | ||
| customSearchEngines = (await configPresenter.getCustomSearchEngines()) || [] | ||
| } catch (error) { | ||
| console.error('获取自定义搜索引擎失败:', error) | ||
| customSearchEngines = [] | ||
| } | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use English for console error messages.
The console.error message contains Chinese text "获取自定义搜索引擎失败:" (line 247), which violates the coding guideline requiring English for all logs and comments.
As per coding guidelines
Apply this diff:
try {
customSearchEngines = (await configPresenter.getCustomSearchEngines()) || []
} catch (error) {
- console.error('获取自定义搜索引擎失败:', error)
+ console.error('Failed to get custom search engines:', error)
customSearchEngines = []
}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| try { | |
| let customSearchEngines: SearchEngineTemplate[] = [] | |
| try { | |
| customSearchEngines = (await configPresenter.getCustomSearchEngines()) || [] | |
| } catch (error) { | |
| console.error('获取自定义搜索引擎失败:', error) | |
| customSearchEngines = [] | |
| } | |
| try { | |
| let customSearchEngines: SearchEngineTemplate[] = [] | |
| try { | |
| customSearchEngines = (await configPresenter.getCustomSearchEngines()) || [] | |
| } catch (error) { | |
| console.error('Failed to get custom search engines:', error) | |
| customSearchEngines = [] | |
| } |
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/SearchEngineSettingsSection.vue
around lines 242 to 250, the console.error message uses Chinese text; replace it
with an English message such as "Failed to get custom search engines:" while
continuing to pass the error object to console.error so the original error
details are preserved.
| closeAddSearchEngineDialog() | ||
| } catch (error) { | ||
| console.error('添加自定义搜索引擎失败:', error) | ||
| } | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use English for console error messages.
The console.error message contains Chinese text "添加自定义搜索引擎失败:" (line 266), which violates the coding guideline requiring English for all logs and comments.
As per coding guidelines
Apply this diff:
closeAddSearchEngineDialog()
} catch (error) {
- console.error('添加自定义搜索引擎失败:', error)
+ console.error('Failed to add custom search engine:', error)
}
}🤖 Prompt for AI Agents
In src/renderer/settings/components/common/SearchEngineSettingsSection.vue
around lines 264 to 268, the console.error message is in Chinese; change it to
an English message such as "Failed to add custom search engine:" and retain
logging of the error object (console.error("Failed to add custom search
engine:", error)); update only that log string so it complies with the
English-only logging guideline.
| try { | ||
| let customSearchEngines: SearchEngineTemplate[] = [] | ||
| try { | ||
| customSearchEngines = (await configPresenter.getCustomSearchEngines()) || [] | ||
| } catch (error) { | ||
| console.error('获取自定义搜索引擎失败:', error) | ||
| customSearchEngines = [] | ||
| } | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use English for console error messages.
The console.error message contains Chinese text "获取自定义搜索引擎失败:" (line 287), which violates the coding guideline requiring English for all logs and comments.
As per coding guidelines
Apply this diff:
try {
customSearchEngines = (await configPresenter.getCustomSearchEngines()) || []
} catch (error) {
- console.error('获取自定义搜索引擎失败:', error)
+ console.error('Failed to get custom search engines:', error)
customSearchEngines = []
}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| try { | |
| let customSearchEngines: SearchEngineTemplate[] = [] | |
| try { | |
| customSearchEngines = (await configPresenter.getCustomSearchEngines()) || [] | |
| } catch (error) { | |
| console.error('获取自定义搜索引擎失败:', error) | |
| customSearchEngines = [] | |
| } | |
| try { | |
| let customSearchEngines: SearchEngineTemplate[] = [] | |
| try { | |
| customSearchEngines = (await configPresenter.getCustomSearchEngines()) || [] | |
| } catch (error) { | |
| console.error('Failed to get custom search engines:', error) | |
| customSearchEngines = [] | |
| } |
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/SearchEngineSettingsSection.vue
around lines 282 to 290, the console.error message uses Chinese text
("获取自定义搜索引擎失败:"); replace it with an English message such as "Failed to get
custom search engines:" while preserving the appended error object and existing
fallback assignment so the log remains informative and behavior unchanged.
| closeDeleteSearchEngineDialog() | ||
| } catch (error) { | ||
| console.error('删除自定义搜索引擎失败:', error) | ||
| } | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use English for console error messages.
The console.error message contains Chinese text "删除自定义搜索引擎失败:" (line 313), which violates the coding guideline requiring English for all logs and comments.
As per coding guidelines
Apply this diff:
closeDeleteSearchEngineDialog()
} catch (error) {
- console.error('删除自定义搜索引擎失败:', error)
+ console.error('Failed to delete custom search engine:', error)
}
}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| closeDeleteSearchEngineDialog() | |
| } catch (error) { | |
| console.error('删除自定义搜索引擎失败:', error) | |
| } | |
| } | |
| closeDeleteSearchEngineDialog() | |
| } catch (error) { | |
| console.error('Failed to delete custom search engine:', error) | |
| } | |
| } |
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/SearchEngineSettingsSection.vue
around lines 311 to 315, the console.error message uses Chinese text; replace
the Chinese string "删除自定义搜索引擎失败:" with an English message such as "Failed to
delete custom search engine:" and keep the error object in the log
(console.error('Failed to delete custom search engine:', error)) so logs conform
to the English-only guideline.
| const increaseWebContentLimit = () => { | ||
| const newValue = Math.min(webContentLengthLimit.value + 100, 20000) | ||
| handleWebContentLengthLimitChange(newValue) | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fix max value inconsistency.
The increaseWebContentLimit function allows values up to 20000, but the UI disable check on line 48 uses 10000 as the maximum. This creates an inconsistent upper bound.
Apply this diff to align the maximum value:
const increaseWebContentLimit = () => {
- const newValue = Math.min(webContentLengthLimit.value + 100, 20000)
+ const newValue = Math.min(webContentLengthLimit.value + 100, 10000)
handleWebContentLengthLimitChange(newValue)
}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| const increaseWebContentLimit = () => { | |
| const newValue = Math.min(webContentLengthLimit.value + 100, 20000) | |
| handleWebContentLengthLimitChange(newValue) | |
| } | |
| const increaseWebContentLimit = () => { | |
| const newValue = Math.min(webContentLengthLimit.value + 100, 10000) | |
| handleWebContentLengthLimitChange(newValue) | |
| } |
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/WebContentLimitSetting.vue around
lines 86 to 89, the increaseWebContentLimit function caps at 20000 while the UI
disable check uses 10000, causing an inconsistent upper bound; change the cap in
increaseWebContentLimit to 10000 (i.e., replace 20000 with 10000) so both the
increment logic and the disable check use the same maximum value.
| webContentLengthLimit.value = savedLimit | ||
| } | ||
| } catch (error) { | ||
| console.error('加载网页内容长度设置失败:', error) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use English for error messages.
The error message uses Chinese, violating the coding guideline: "Use English for all logs and comments."
As per coding guidelines.
Apply this diff:
- console.error('加载网页内容长度设置失败:', error)
+ console.error('Failed to load web content length setting:', error)📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| console.error('加载网页内容长度设置失败:', error) | |
| console.error('Failed to load web content length setting:', error) |
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/WebContentLimitSetting.vue around
line 121, the console.error message is written in Chinese; change it to an
English message such as "Failed to load web content length setting:" while
preserving the appended error variable so the logged error details remain
available; update the string only and keep the rest of the console.error call
unchanged.
| } catch (error) { | ||
| const errorMessage = error instanceof Error ? error.message : String(error) | ||
| toast({ | ||
| title: t('promptSetting.importFailed'), | ||
| description: `错误: ${errorMessage}`, | ||
| variant: 'destructive' | ||
| }) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use i18n for error messages.
The error description contains a hardcoded Chinese string "错误:" (line 474), which violates the coding guideline requiring English for all logs and user-facing text. This should use the i18n system for proper localization.
As per coding guidelines
Apply this diff to use i18n:
} catch (error) {
const errorMessage = error instanceof Error ? error.message : String(error)
toast({
title: t('promptSetting.importFailed'),
- description: `错误: ${errorMessage}`,
+ description: t('promptSetting.importError', { error: errorMessage }),
variant: 'destructive'
})
}Then add the i18n key to your localization files:
// In your i18n locale files
promptSetting: {
importError: 'Error: {error}'
}🤖 Prompt for AI Agents
In src/renderer/settings/components/prompt/CustomPromptSettingsSection.vue
around lines 470 to 476, the catch block currently uses a hardcoded Chinese
prefix "错误:" for the toast description; replace it with the i18n call so the
message uses t('promptSetting.importError', { error: errorMessage }) (or
equivalent i18n helper) instead of the literal string, and add the corresponding
key to the locale files (promptSetting.importError = 'Error: {error}' in the
English file and the appropriate translation in other locales).
| reader.onerror = () => { | ||
| toast({ | ||
| title: t('promptSetting.importFailed'), | ||
| description: '文件读取失败', | ||
| variant: 'destructive' | ||
| }) | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use i18n for error messages.
The error description contains a hardcoded Chinese string "文件读取失败" (line 483), which violates the coding guideline requiring English for all logs and user-facing text. This should use the i18n system for proper localization.
As per coding guidelines
Apply this diff to use i18n:
reader.onerror = () => {
toast({
title: t('promptSetting.importFailed'),
- description: '文件读取失败',
+ description: t('promptSetting.fileReadFailed'),
variant: 'destructive'
})
}Then add the i18n key to your localization files:
// In your i18n locale files
promptSetting: {
fileReadFailed: 'File read failed'
}🤖 Prompt for AI Agents
In src/renderer/settings/components/prompt/CustomPromptSettingsSection.vue
around lines 480 to 486, the toast error description is hardcoded as the Chinese
string "文件读取失败"; replace this with the i18n lookup (use the t() function) so the
message is localized (e.g., t('promptSetting.fileReadFailed')), and update the
app locale files to include promptSetting.fileReadFailed: 'File read failed'
(and translations) so the i18n key resolves properly.
| <Textarea | ||
| id="system-prompt-content" | ||
| v-model="form.content" | ||
| class="w-full h-64" | ||
| :placeholder="t('promptSetting.contentPlaceholder')" | ||
| /> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Apply monospace and resizable styling to match PR objectives.
The PR description states "reinstates a monospace, resizable content textarea for consistency," but this textarea lacks those styles.
Apply this diff to add the missing styles:
<Textarea
id="system-prompt-content"
v-model="form.content"
- class="w-full h-64"
+ class="w-full h-64 font-mono resize-y"
:placeholder="t('promptSetting.contentPlaceholder')"
/>📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| <Textarea | |
| id="system-prompt-content" | |
| v-model="form.content" | |
| class="w-full h-64" | |
| :placeholder="t('promptSetting.contentPlaceholder')" | |
| /> | |
| <Textarea | |
| id="system-prompt-content" | |
| v-model="form.content" | |
| class="w-full h-64 font-mono resize-y" | |
| :placeholder="t('promptSetting.contentPlaceholder')" | |
| /> |
🤖 Prompt for AI Agents
In src/renderer/settings/components/prompt/SystemPromptEditorSheet.vue around
lines 42 to 47, the Textarea lacks monospace and resizable styles—update the
component's class list to include a monospace font and enable resizing (for
example add font-mono and a resize class such as resize-y or resize) so the
textarea is rendered in a monospace typeface and is user-resizable while
preserving existing layout classes like w-full h-64.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 2
♻️ Duplicate comments (6)
src/renderer/settings/components/common/SearchEngineSettingsSection.vue (6)
250-250: Use English for console error messages.This Chinese console.error message violates the coding guideline requiring English for all logs.
As per coding guidelines
269-269: Use English for console error messages.This Chinese console.error message violates the coding guideline requiring English for all logs.
As per coding guidelines
290-290: Use English for console error messages.This Chinese console.error message violates the coding guideline requiring English for all logs.
As per coding guidelines
316-316: Use English for console error messages.This Chinese console.error message violates the coding guideline requiring English for all logs.
As per coding guidelines
333-333: Use English for console error messages.This Chinese console.error message violates the coding guideline requiring English for all logs.
As per coding guidelines
1-353: Fix Prettier formatting issues.The file fails Prettier validation. Run
pnpm run formatto automatically fix code style issues.Run the following command:
pnpm run format
🧹 Nitpick comments (4)
src/renderer/settings/components/common/SettingToggleRow.vue (2)
1-18: Consider applyingdirto the entire row for consistent RTL layout.Currently, the
dirattribute is only applied to the label span (line 5). In RTL languages, the entire row layout should reverse, including the switch position. Moving thedirattribute to the rootdivwould ensure consistent RTL behavior.Apply this diff to improve RTL support:
-<div class="flex items-center gap-3 h-10"> +<div class="flex items-center gap-3 h-10" :dir="langStore.dir"> <span class="flex items-center gap-2 text-sm font-medium shrink-0 min-w-[220px]" - :dir="langStore.dir" >
20-32: Optional: simplify by removing toRefs.The
toRefsdestructuring on line 31 is valid but potentially unnecessary. In Vue 3 script setup, props are already reactive, so you can use them directly in the template (e.g.,props.icon,props.label). The current approach works but adds slight verbosity.If you prefer a more concise approach, apply this diff:
-const { id, icon, label, modelValue } = toRefs(props)And update the template to use
props.icon,props.label,props.id,props.modelValuedirectly. Alternatively, keep the current pattern for consistency if toRefs is used elsewhere in the codebase.src/renderer/settings/components/common/ProxySettingsSection.vue (1)
95-97: Simplify condition by removing redundant empty check.The condition at line 95 checks
!customProxyUrl.value.trim(), but this is redundant since lines 83-86 already handle the empty case with an early return. The second part of the OR condition can never be true at this point.Apply this diff to simplify the condition:
- if (isValid || !customProxyUrl.value.trim()) { + if (isValid) { configPresenter.setCustomProxyUrl(customProxyUrl.value) }src/renderer/settings/components/common/SearchEngineSettingsSection.vue (1)
328-335: Consider using an English test query for consistency.The hardcoded Chinese test query '天气' should be replaced with an English equivalent (e.g., 'weather') for code consistency and maintainability.
Apply this diff:
const testSearchEngine = async () => { try { - await settingsStore.testSearchEngine('天气') + await settingsStore.testSearchEngine('weather') closeTestSearchEngineDialog() } catch (error) { console.error('测试搜索引擎失败:', error) } }As per coding guidelines
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (6)
src/renderer/settings/components/common/LoggingSettingsSection.vue(1 hunks)src/renderer/settings/components/common/ProxySettingsSection.vue(1 hunks)src/renderer/settings/components/common/SearchAssistantModelSection.vue(1 hunks)src/renderer/settings/components/common/SearchEngineSettingsSection.vue(1 hunks)src/renderer/settings/components/common/SettingToggleRow.vue(1 hunks)src/renderer/settings/components/common/WebContentLimitSetting.vue(1 hunks)
🚧 Files skipped from review as they are similar to previous changes (2)
- src/renderer/settings/components/common/LoggingSettingsSection.vue
- src/renderer/settings/components/common/WebContentLimitSetting.vue
🧰 Additional context used
📓 Path-based instructions (9)
src/renderer/**/*.{vue,ts,js,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/project-structure.mdc)
渲染进程代码放在
src/renderer
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
src/renderer/**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,tsx,vue}: Use descriptive variable names with auxiliary verbs (e.g., isLoading, hasError).
Use TypeScript for all code; prefer types over interfaces.
Avoid enums; use const objects instead.
Use arrow functions for methods and computed properties.
Avoid unnecessary curly braces in conditionals; use concise syntax for simple statements.
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
src/renderer/**/*.{vue,ts}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
Implement lazy loading for routes and components.
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
src/renderer/**/*.{ts,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,vue}: Use useFetch and useAsyncData for data fetching.
Implement SEO best practices using Nuxt's useHead and useSeoMeta.Use Pinia for frontend state management (do not introduce alternative state libraries)
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
**/*.{ts,tsx,js,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Use English for all logs and comments
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Enable and adhere to strict TypeScript typing (avoid implicit any, prefer precise types)
Use PascalCase for TypeScript types and classes
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
**/*.{ts,tsx,js,jsx,vue,css,scss,md,json,yml,yaml}
📄 CodeRabbit inference engine (AGENTS.md)
Prettier style: single quotes, no semicolons, print width 100; run pnpm run format
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (AGENTS.md)
**/*.{ts,tsx,js,jsx,vue}: Use OxLint for JS/TS code; keep lint clean
Use camelCase for variables and functions
Use SCREAMING_SNAKE_CASE for constants
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
src/renderer/**/*.vue
📄 CodeRabbit inference engine (AGENTS.md)
Name Vue component files in PascalCase (e.g., ChatInput.vue)
Files:
src/renderer/settings/components/common/SettingToggleRow.vuesrc/renderer/settings/components/common/ProxySettingsSection.vuesrc/renderer/settings/components/common/SearchAssistantModelSection.vuesrc/renderer/settings/components/common/SearchEngineSettingsSection.vue
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: build-check (x64)
🔇 Additional comments (8)
src/renderer/settings/components/common/SettingToggleRow.vue (1)
11-15: Verify Switch component accessibility: ensure theidprop on<Switch>is applied to its underlying input and used for semantic labelling (e.g.,aria-labelledbyoraria-label) since there’s no explicit<label>in this row.src/renderer/settings/components/common/SearchEngineSettingsSection.vue (7)
1-150: Template structure looks good.The UI layout is well-organized with proper Vue bindings, conditional rendering, and accessibility attributes. Dialog implementations follow shadcn component patterns correctly.
152-183: LGTM!Imports are properly organized and typed. The setup follows Vue 3 Composition API conventions and project structure.
185-213: State management and computed properties are well-implemented.The reactive state is clearly organized, and computed properties provide appropriate derived values with proper validation logic.
215-226: LGTM!Dialog handlers properly reset form state and manage visibility.
228-271: Add custom search engine logic is correct.The function properly validates input, creates a unique ID, persists the new engine, updates the store, and selects the newly added engine. The nested try-catch for fetching existing engines provides appropriate fallback handling.
273-318: Delete search engine logic handles edge cases well.The function properly handles the case where the active engine is being deleted by falling back to the first default engine. State management and persistence are correctly implemented.
337-352: Watchers and lifecycle hooks are correctly implemented.The bidirectional sync between local
selectedSearchEngineandsettingsStore.activeSearchEngineis properly handled with conditional checks to prevent infinite loops. Initialization inonMountedis appropriate.
| <div v-if="selectedProxyMode === 'custom'" class="flex flex-col gap-2 h-10"> | ||
| <div class="flex items-center gap-3"> | ||
| <span | ||
| class="flex items-center gap-2 text-sm font-medium shrink-0 min-w-[220px]" | ||
| :dir="langStore.dir" | ||
| > | ||
| <Icon icon="lucide:link" class="w-4 h-4 text-muted-foreground" /> | ||
| <span class="truncate">{{ t('settings.common.customProxyUrl') }}</span> | ||
| </span> | ||
| <div class="ml-auto w-[320px]"> | ||
| <Input | ||
| v-model="customProxyUrl" | ||
| :placeholder="t('settings.common.customProxyUrlPlaceholder')" | ||
| :class="{ 'border-red-500': showUrlError }" | ||
| @input="validateProxyUrl" | ||
| @blur="validateProxyUrl" | ||
| /> | ||
| </div> | ||
| </div> | ||
| <div v-if="showUrlError" class="text-xs text-red-500 pt-1 lg:pl-[220px] pl-10"> | ||
| {{ t('settings.common.invalidProxyUrl') }} | ||
| </div> | ||
| </div> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Remove fixed height constraint to prevent content clipping.
The h-10 class on line 25 sets a fixed height of 2.5rem, but the flex column layout contains an input (minimum h-8) plus an error message with padding. When the validation error displays, the content will exceed the fixed height constraint, causing layout issues or content clipping.
Apply this diff to remove the height constraint:
- <div v-if="selectedProxyMode === 'custom'" class="flex flex-col gap-2 h-10">
+ <div v-if="selectedProxyMode === 'custom'" class="flex flex-col gap-2">📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| <div v-if="selectedProxyMode === 'custom'" class="flex flex-col gap-2 h-10"> | |
| <div class="flex items-center gap-3"> | |
| <span | |
| class="flex items-center gap-2 text-sm font-medium shrink-0 min-w-[220px]" | |
| :dir="langStore.dir" | |
| > | |
| <Icon icon="lucide:link" class="w-4 h-4 text-muted-foreground" /> | |
| <span class="truncate">{{ t('settings.common.customProxyUrl') }}</span> | |
| </span> | |
| <div class="ml-auto w-[320px]"> | |
| <Input | |
| v-model="customProxyUrl" | |
| :placeholder="t('settings.common.customProxyUrlPlaceholder')" | |
| :class="{ 'border-red-500': showUrlError }" | |
| @input="validateProxyUrl" | |
| @blur="validateProxyUrl" | |
| /> | |
| </div> | |
| </div> | |
| <div v-if="showUrlError" class="text-xs text-red-500 pt-1 lg:pl-[220px] pl-10"> | |
| {{ t('settings.common.invalidProxyUrl') }} | |
| </div> | |
| </div> | |
| <div v-if="selectedProxyMode === 'custom'" class="flex flex-col gap-2"> | |
| <div class="flex items-center gap-3"> | |
| <span | |
| class="flex items-center gap-2 text-sm font-medium shrink-0 min-w-[220px]" | |
| :dir="langStore.dir" | |
| > | |
| <Icon icon="lucide:link" class="w-4 h-4 text-muted-foreground" /> | |
| <span class="truncate">{{ t('settings.common.customProxyUrl') }}</span> | |
| </span> | |
| <div class="ml-auto w-[320px]"> | |
| <Input | |
| v-model="customProxyUrl" | |
| :placeholder="t('settings.common.customProxyUrlPlaceholder')" | |
| :class="{ 'border-red-500': showUrlError }" | |
| @input="validateProxyUrl" | |
| @blur="validateProxyUrl" | |
| /> | |
| </div> | |
| </div> | |
| <div v-if="showUrlError" class="text-xs text-red-500 pt-1 lg:pl-[220px] pl-10"> | |
| {{ t('settings.common.invalidProxyUrl') }} | |
| </div> | |
| </div> |
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/ProxySettingsSection.vue around lines
25 to 47, the outer div has a fixed height class "h-10" that causes input and
the error message to clip when the validation error appears; remove the "h-10"
class from that div (leaving the flex, flex-col, and gap-2) so the container can
grow with its contents and the error text won't be clipped, ensuring existing
padding/margin and responsive layout remain unchanged.
| const handleSearchModelSelect = (model: RENDERER_MODEL_META, providerId: string) => { | ||
| settingsStore.setSearchAssistantModel(model, providerId) | ||
| modelSelectOpen.value = false | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fix handleSearchModelSelect signature.
ModelSelect’s update:model event only passes the chosen model payload. The handler’s second parameter is therefore undefined, and the store update ends up calling setSearchAssistantModel(model, undefined). Adjust the handler to accept the payload actually emitted (include provider in the payload or fetch it from the model) before updating the store.
🤖 Prompt for AI Agents
In src/renderer/settings/components/common/SearchAssistantModelSection.vue
around lines 63-66, the handler currently expects (model, providerId) but the
ModelSelect update:model event emits only the selected model payload so
providerId is undefined; change the handler to accept the actual emitted payload
(either a combined payload that includes provider or just the model) and obtain
the providerId from that payload or derive it from the model object, then call
settingsStore.setSearchAssistantModel(model, providerId) with the real provider
value and keep modelSelectOpen.value = false.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (2)
src/renderer/settings/components/common/LoggingSettingsSection.vue (2)
77-84: Consider resetting preview state on cancel for cleanliness.While not strictly necessary (since
newLoggingValueis only used for dialog text and the switch reverts automatically), resetting it when cancelling improves state hygiene.Apply this diff:
const cancelLoggingChange = () => { + newLoggingValue.value = loggingEnabled.value isLoggingDialogOpen.value = false }
91-93: Add error handling for the log folder operation.The
openLoggingFoldercall could fail silently if the folder doesn't exist or the system operation fails. Consider wrapping it in a try-catch block or displaying a notification on failure.Apply this diff:
const openLogFolder = () => { - configPresenter.openLoggingFolder() + try { + configPresenter.openLoggingFolder() + } catch (error) { + console.error('Failed to open log folder:', error) + // Consider showing a toast/notification to the user + } }
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (2)
src/renderer/settings/components/CommonSettings.vue(1 hunks)src/renderer/settings/components/common/LoggingSettingsSection.vue(1 hunks)
🧰 Additional context used
📓 Path-based instructions (9)
src/renderer/**/*.{vue,ts,js,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/project-structure.mdc)
渲染进程代码放在
src/renderer
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,tsx,vue}: Use descriptive variable names with auxiliary verbs (e.g., isLoading, hasError).
Use TypeScript for all code; prefer types over interfaces.
Avoid enums; use const objects instead.
Use arrow functions for methods and computed properties.
Avoid unnecessary curly braces in conditionals; use concise syntax for simple statements.
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.{vue,ts}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
Implement lazy loading for routes and components.
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.{ts,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,vue}: Use useFetch and useAsyncData for data fetching.
Implement SEO best practices using Nuxt's useHead and useSeoMeta.Use Pinia for frontend state management (do not introduce alternative state libraries)
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,js,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Use English for all logs and comments
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Enable and adhere to strict TypeScript typing (avoid implicit any, prefer precise types)
Use PascalCase for TypeScript types and classes
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,js,jsx,vue,css,scss,md,json,yml,yaml}
📄 CodeRabbit inference engine (AGENTS.md)
Prettier style: single quotes, no semicolons, print width 100; run pnpm run format
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (AGENTS.md)
**/*.{ts,tsx,js,jsx,vue}: Use OxLint for JS/TS code; keep lint clean
Use camelCase for variables and functions
Use SCREAMING_SNAKE_CASE for constants
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.vue
📄 CodeRabbit inference engine (AGENTS.md)
Name Vue component files in PascalCase (e.g., ChatInput.vue)
Files:
src/renderer/settings/components/CommonSettings.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: build-check (x64)
🔇 Additional comments (4)
src/renderer/settings/components/common/LoggingSettingsSection.vue (1)
1-48: LGTM! Clean template structure with good UX pattern.The template correctly implements a confirmation dialog pattern where the switch appears to change immediately (visual feedback) but requires confirmation. If the user cancels or closes the dialog, the switch automatically reverts to the store value since it's bound via
:model-value. The i18n integration and RTL support vialangStore.dirare well-implemented.src/renderer/settings/components/CommonSettings.vue (3)
4-29: Excellent refactoring! Clean modularization improves maintainability.The replacement of inline UI blocks with dedicated components (
SearchEngineSettingsSection,WebContentLimitSetting,SearchAssistantModelSection,ProxySettingsSection,LoggingSettingsSection) and the consistent use ofSettingToggleRowfor toggle switches significantly improves code organization and follows the DRY principle. This modular approach makes the codebase easier to maintain and test.
40-45: Component imports follow PascalCase naming convention.All component imports correctly use PascalCase, which aligns with the coding guidelines for Vue component file names.
As per coding guidelines.
51-65: Clean handler implementation with proper store delegation.The computed properties and handlers follow the composition API patterns correctly, with simple delegation to the respective stores. The code is clean, readable, and maintainable.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🧹 Nitpick comments (2)
src/renderer/settings/components/common/LoggingSettingsSection.vue (2)
20-26: Add RTL support for switch positioning.The switch uses
ml-autoto align right, but in RTL layouts it should align left. Use logical properties or directional classes for proper RTL support.Apply this diff to fix the RTL layout:
<Switch id="logging-switch" - class="ml-auto" + class="ltr:ml-auto rtl:mr-auto" :model-value="loggingEnabled" @update:model-value="handleLoggingChange" />
90-97: Consider adding error handling for external calls.The calls to
settingsStore.setLoggingEnabledandconfigPresenter.openLoggingFolderhave no error handling. If these operations fail, the user receives no feedback.Consider adding try-catch blocks or error toasts:
const confirmLoggingChange = async () => { try { await settingsStore.setLoggingEnabled(newLoggingValue.value) isLoggingDialogOpen.value = false } catch (error) { console.error('Failed to update logging setting:', error) // Show error toast to user } } const openLogFolder = async () => { try { await configPresenter.openLoggingFolder() } catch (error) { console.error('Failed to open log folder:', error) // Show error toast to user } }
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (2)
src/renderer/settings/components/common/LoggingSettingsSection.vue(1 hunks)src/renderer/settings/components/prompt/PromptEditorSheet.vue(1 hunks)
🧰 Additional context used
📓 Path-based instructions (9)
src/renderer/**/*.{vue,ts,js,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/project-structure.mdc)
渲染进程代码放在
src/renderer
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,tsx,vue}: Use descriptive variable names with auxiliary verbs (e.g., isLoading, hasError).
Use TypeScript for all code; prefer types over interfaces.
Avoid enums; use const objects instead.
Use arrow functions for methods and computed properties.
Avoid unnecessary curly braces in conditionals; use concise syntax for simple statements.
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.{vue,ts}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
Implement lazy loading for routes and components.
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.{ts,vue}
📄 CodeRabbit inference engine (.cursor/rules/vue-shadcn.mdc)
src/renderer/**/*.{ts,vue}: Use useFetch and useAsyncData for data fetching.
Implement SEO best practices using Nuxt's useHead and useSeoMeta.Use Pinia for frontend state management (do not introduce alternative state libraries)
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,js,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Use English for all logs and comments
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,vue}
📄 CodeRabbit inference engine (CLAUDE.md)
Enable and adhere to strict TypeScript typing (avoid implicit any, prefer precise types)
Use PascalCase for TypeScript types and classes
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,js,jsx,vue,css,scss,md,json,yml,yaml}
📄 CodeRabbit inference engine (AGENTS.md)
Prettier style: single quotes, no semicolons, print width 100; run pnpm run format
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (AGENTS.md)
**/*.{ts,tsx,js,jsx,vue}: Use OxLint for JS/TS code; keep lint clean
Use camelCase for variables and functions
Use SCREAMING_SNAKE_CASE for constants
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
src/renderer/**/*.vue
📄 CodeRabbit inference engine (AGENTS.md)
Name Vue component files in PascalCase (e.g., ChatInput.vue)
Files:
src/renderer/settings/components/prompt/PromptEditorSheet.vuesrc/renderer/settings/components/common/LoggingSettingsSection.vue
🔇 Additional comments (4)
src/renderer/settings/components/common/LoggingSettingsSection.vue (4)
28-50: LGTM!The dialog structure correctly implements a confirmation pattern with appropriate cancel handling via
@update:open, conditional messaging, and clear action buttons.
54-76: LGTM!The imports and setup follow the project's conventions correctly, using composables, stores, and i18n as expected.
77-79: LGTM!The reactive state is properly structured with a computed property from the store and refs for local component state.
81-93: Switch component correctly delegatesmodelValue; no UX issue detected. The wrapper forwards props and emits without internal state, so cancelling the dialog will automatically revert the switch.
| <SheetContent | ||
| side="right" | ||
| class="w-[75vw]! max-w-[95vw]! h-screen flex flex-col p-0 bg-background window-no-drag-region" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fix Tailwind important syntax on sheet width.
w-[75vw]! / max-w-[95vw]! don’t resolve in Tailwind (important modifiers must prefix the class), so the sheet keeps the default narrow width and the layout regresses. Switch to the ! prefix form.
- class="w-[75vw]! max-w-[95vw]! h-screen flex flex-col p-0 bg-background window-no-drag-region"
+ class="!w-[75vw] !max-w-[95vw] h-screen flex flex-col p-0 bg-background window-no-drag-region"📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| <SheetContent | |
| side="right" | |
| class="w-[75vw]! max-w-[95vw]! h-screen flex flex-col p-0 bg-background window-no-drag-region" | |
| <SheetContent | |
| side="right" | |
| class="!w-[75vw] !max-w-[95vw] h-screen flex flex-col p-0 bg-background window-no-drag-region" |
🤖 Prompt for AI Agents
In src/renderer/settings/components/prompt/PromptEditorSheet.vue around lines 3
to 5, the Tailwind "important" modifier is currently suffixed (w-[75vw]! and
max-w-[95vw]!) which Tailwind doesn't recognize; change them to the prefix form
(!w-[75vw] and !max-w-[95vw]) so the sheet width/max-width are applied
correctly, preserving the rest of the class string and layout.
Summary
Testing
https://chatgpt.com/codex/tasks/task_e_68ee345049e8832c94c64148ba469370
Summary by CodeRabbit