Skip to content

feat(skill): add draft confirmation card with view/install/discard#1687

Merged
zerob13 merged 2 commits into
devfrom
skill-draft
May 28, 2026
Merged

feat(skill): add draft confirmation card with view/install/discard#1687
zerob13 merged 2 commits into
devfrom
skill-draft

Conversation

@zhangmo8
Copy link
Copy Markdown
Collaborator

@zhangmo8 zhangmo8 commented May 28, 2026

c52b8d44-78e1-4f0a-811e-4191bd245081 dcceedc0-1faa-4909-8dd7-ed3a182de4eb e5c92fe1-2a35-438c-9ad5-302dbd539a97

Summary by CodeRabbit

  • New Features

    • Interactive skill-draft confirmation card appears in chat after a draft is created, letting users preview, view, install, or discard a draft.
    • Inline handling option ensures previewing a draft can keep the interaction open without resuming the assistant turn.
  • Documentation

    • Feature plan, spec, and task checklist added for the skill-draft confirmation card.
  • Tests

    • Expanded unit tests covering draft creation, preview, view/install/discard flows and UI interactions.

Review Change Stack

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 28, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 76e9e2a6-6c04-44c3-929d-f659b72e90e4

📥 Commits

Reviewing files that changed from the base of the PR and between 76daa16 and 9a86ed8.

📒 Files selected for processing (19)
  • src/renderer/src/i18n/da-DK/chat.json
  • src/renderer/src/i18n/de-DE/chat.json
  • src/renderer/src/i18n/es-ES/chat.json
  • src/renderer/src/i18n/fa-IR/chat.json
  • src/renderer/src/i18n/fr-FR/chat.json
  • src/renderer/src/i18n/he-IL/chat.json
  • src/renderer/src/i18n/id-ID/chat.json
  • src/renderer/src/i18n/it-IT/chat.json
  • src/renderer/src/i18n/ja-JP/chat.json
  • src/renderer/src/i18n/ko-KR/chat.json
  • src/renderer/src/i18n/ms-MY/chat.json
  • src/renderer/src/i18n/pl-PL/chat.json
  • src/renderer/src/i18n/pt-BR/chat.json
  • src/renderer/src/i18n/ru-RU/chat.json
  • src/renderer/src/i18n/tr-TR/chat.json
  • src/renderer/src/i18n/vi-VN/chat.json
  • src/renderer/src/i18n/zh-CN/chat.json
  • src/renderer/src/i18n/zh-HK/chat.json
  • src/renderer/src/i18n/zh-TW/chat.json
✅ Files skipped from review due to trivial changes (13)
  • src/renderer/src/i18n/ja-JP/chat.json
  • src/renderer/src/i18n/it-IT/chat.json
  • src/renderer/src/i18n/de-DE/chat.json
  • src/renderer/src/i18n/ms-MY/chat.json
  • src/renderer/src/i18n/fa-IR/chat.json
  • src/renderer/src/i18n/zh-CN/chat.json
  • src/renderer/src/i18n/da-DK/chat.json
  • src/renderer/src/i18n/pl-PL/chat.json
  • src/renderer/src/i18n/id-ID/chat.json
  • src/renderer/src/i18n/vi-VN/chat.json
  • src/renderer/src/i18n/he-IL/chat.json
  • src/renderer/src/i18n/es-ES/chat.json
  • src/renderer/src/i18n/zh-HK/chat.json
🚧 Files skipped from review as they are similar to previous changes (6)
  • src/renderer/src/i18n/fr-FR/chat.json
  • src/renderer/src/i18n/zh-TW/chat.json
  • src/renderer/src/i18n/ru-RU/chat.json
  • src/renderer/src/i18n/ko-KR/chat.json
  • src/renderer/src/i18n/pt-BR/chat.json
  • src/renderer/src/i18n/tr-TR/chat.json

📝 Walkthrough

Walkthrough

Adds an in-chat skill draft confirmation card flow: tool responses include structured draft metadata, runtime dispatch enqueues a question_request with view/install/discard options, presenter methods for draft view/install/discard are implemented, renderer shows preview and localized option labels, and tests cover end-to-end behavior.

Changes

Skill Draft Confirmation Card

Layer / File(s) Summary
Type Contracts and State Extensions
src/shared/types/skill.ts, src/shared/types/core/chat.ts, src/shared/types/agent-interface.d.ts, src/shared/chat.d.ts, src/shared/contracts/common.ts
New types define SkillDraftUserAction ('view'
Skill Presenter Draft Operations
src/main/presenter/skillPresenter/index.ts
Adds viewDraftSkill, installDraftSkill, discardDraftSkill; manageDraftSkill create/edit now include draftStatus; installFromDirectory adds stricter SKILL_NAME_PATTERN validation; adds helper to remove empty conversation draft dirs.
Skill Manage Tool Result Enrichment
src/main/presenter/toolPresenter/agentTools/agentToolManager.ts
Builds structured rawData.toolResult for skill_manage, including toolName and conditional skillDraft payload when create succeeds; sets rawData.isError from result success flag.
Runtime Dispatch and Question Queuing
src/main/presenter/agentRuntimePresenter/dispatch.ts, types.ts
Extracts skillDraftPrompt from tool results with skillDraft.status === 'created', stages it on tool runs, and appends a pending question_request action with skill-draft confirmation options; appendQuestionActionBlock accepts extra; merges/clears state.pendingInteractions across execution paths.
Runtime Interaction Handler
src/main/presenter/agentRuntimePresenter/index.ts
Adds enums/helpers to detect skill-draft confirmation blocks, resolve user choice, populate options, serialize responses, and handle view/install/discard flows in respondToolInteraction (can keep pending or resume streaming and update message block metadata/status). Extends runtime-port typing for draft methods.
Frontend Rendering Components
src/renderer/src/components/chat/ChatToolInteractionOverlay.vue, src/renderer/src/components/message/MessageBlockQuestionRequest.vue, src/renderer/src/components/chat/messageListItems.ts, src/renderer/src/pages/ChatPage.vue
Overlay shows draft preview when present; translation-aware helpers treat dotted strings as i18n keys and inject draft name; question options parse arrays or JSON-strings and provide raw vs translated labels; onToolInteractionRespond short-circuits when handledInline is true.
i18n Translations and Feature Documentation
src/renderer/src/i18n/{da-DK,de-DE,en-US,es-ES,fa-IR,fr-FR,he-IL,id-ID,it-IT,ja-JP,ko-KR,ms-MY,pl-PL,pt-BR,ru-RU,tr-TR,vi-VN,zh-CN,zh-HK,zh-TW}/chat.json, docs/features/skill-draft-confirmation-card/{plan.md,spec.md,tasks.md}
Adds skillDraft or onboarding.skillDraft translation blocks across locales with confirmation/preview texts, action labels/descriptions (view/install/discard), and result messages; feature docs added/updated (plan, spec, tasks).
Comprehensive Test Coverage
test/main/presenter/agentRuntimePresenter/{agentRuntimePresenter.test.ts,dispatch.test.ts}, test/main/presenter/skillPresenter/skillPresenter.test.ts, test/main/presenter/toolPresenter/agentTools/agentToolManagerSettings.test.ts, test/renderer/components/{ChatPage.test.ts,message/MessageBlockBasics.test.ts}
Extends presenter mocks for draft methods; adds dispatch test ensuring pending question_request on draft create; adds respondToolInteraction tests for view/install/discard behaviors; adds SkillPresenter tests for view/install/discard side effects; updates agentToolManager test expectations and renderer tests for inline handling and preview rendering.

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

  • ThinkInAIXYZ/deepchat#1298: Prior work on question-request generation/handling that this change extends for skill-draft confirmation.

"I'm a rabbit, nibbling code with delight,
A draft appears, choose view, install, or flight.
Preview hops in, options align,
Install or discard — the choice is thine,
Tiny paws applaud the feature's light." 🐰

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and specifically summarizes the main change: adding a draft confirmation card feature with view/install/discard actions for generated skills.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch skill-draft

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 7

🧹 Nitpick comments (1)
src/renderer/src/i18n/zh-CN/chat.json (1)

73-73: 💤 Low value

Consider consistent section ordering across locales.

The skillDraft section appears after the input section (line 73) in zh-CN, but appears after the onboarding section (line ~384) in all other locale files. While JSON key order has no functional impact, consistent ordering improves maintainability.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/renderer/src/i18n/zh-CN/chat.json` at line 73, Move the "skillDraft"
object in zh-CN chat.json from its current position after the "input" section to
follow the "onboarding" section so the key ordering matches other locales;
specifically locate the "skillDraft" key and cut/paste the entire object to
immediately after the "onboarding" key, adjust surrounding commas to keep valid
JSON, and run a quick JSON lint to confirm no syntax errors.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/main/presenter/agentRuntimePresenter/dispatch.ts`:
- Around line 416-435: The extractor currently accepts any MCPToolResponse that
contains toolResult.skillDraft; restrict it to only trust responses from the
known/trusted skill-draft tool by checking the tool identity first (e.g.,
compare rawData.toolName or rawData.toolExecution.name/id against a single
trusted constant like SKILL_DRAFT_TOOL_NAME or an allowlist) before reading
toolResult.skillDraft; if the tool identity does not match, return undefined.
Apply the same guard in the other occurrence referenced (around the other
extract call at the later location) so only the trusted tool can trigger the
draft prompt flow.

In `@src/main/presenter/agentRuntimePresenter/index.ts`:
- Around line 302-310: The code exposes draft-confirmation actions through an
optional skillPresenter which can be undefined and cause runtime throws when a
user triggers a draft action; either make the draft methods required on
skillPresenter or short-circuit before showing/enqueuing the confirmation. Fix
by updating the presenter field or call sites that enqueue confirmations: ensure
the private readonly skillPresenter property includes non-optional
'viewDraftSkill', 'installDraftSkill', and 'discardDraftSkill' (so callers must
supply them), or add a guard in the confirmation/enqueue logic (check if
!this.skillPresenter or missing methods) and immediately resolve/return a clean
error/disabled response instead of displaying the confirmation UI. Update the
same pattern where draft actions are enqueued (the other occurrences referenced
around the file) so every draft-confirmation path checks skillPresenter presence
before proceeding.

In `@src/main/presenter/skillPresenter/index.ts`:
- Around line 2467-2477: The cleanup function removeEmptyDraftConversationDir
currently runs for install/discard flows but not when manageDraftSkill is
invoked with action 'delete', leaving empty conversation folders; update the
manageDraftSkill handler (the function named manageDraftSkill and its 'delete'
branch) to call this.removeEmptyDraftConversationDir(conversationId) after the
deletion completes (same place it’s called for 'install'/'discard') so the
per-conversation draft directory is removed when empty.

In `@src/renderer/src/i18n/da-DK/chat.json`:
- Around line 384-401: The skillDraft localization block is still in English;
update the da-DK chat.json "skillDraft" entries to Danish by replacing each
string: set confirmationTitle to "Udkast til færdighed", confirmationQuestion to
"Et færdighedsudkast er oprettet: {name}", previewTitle to "Forhåndsvisning af
udkastindhold", actions.view to "Vis indhold", actions.viewDescription to
"Forhåndsvis udkastets indhold", actions.install to "Installer som færdighed",
actions.installDescription to "Installer udkastet i færdighedsmappen",
actions.discard to "Forkast", actions.discardDescription to "Slet det
midlertidige udkast", and result.viewed/installed/discarded/failed to "Udkast
vist"/"Udkast installeret"/"Udkast forkastet"/"Udkast-handling mislykkedes"
respectively so Danish users see fully localized strings for the new flow.

In `@src/renderer/src/i18n/de-DE/chat.json`:
- Around line 384-401: The German locale's skillDraft block contains English
strings; update the "skillDraft" object keys (confirmationTitle,
confirmationQuestion, previewTitle, actions.view, actions.viewDescription,
actions.install, actions.installDescription, actions.discard,
actions.discardDescription, and result.*) with proper German translations,
preserving placeholders like {name} exactly and keeping
punctuation/capitalization consistent with other de-DE entries; ensure messages
for "viewed", "installed", "discarded", and "failed" are translated into German
as well.

In `@src/renderer/src/i18n/es-ES/chat.json`:
- Around line 384-401: Translate the English strings under the "skillDraft" key
into Spanish: update "confirmationTitle", "confirmationQuestion",
"previewTitle", all entries under "actions" (view, viewDescription, install,
installDescription, discard, discardDescription) and all entries under "result"
(viewed, installed, discarded, failed) so the es-ES locale is fully Spanish;
keep placeholders like {name} intact and use natural Spanish phrases (e.g.,
"Borrador de habilidad", "Se ha generado un borrador: {name}", "Vista previa del
contenido", "Ver contenido", "Instalar como habilidad", "Descartar", "Acción de
borrador fallida", etc.) while preserving key names ("skillDraft" and nested
keys) exactly.

In `@src/renderer/src/i18n/pl-PL/chat.json`:
- Around line 384-401: The skillDraft block contains English strings; replace
each value under "skillDraft" with Polish translations while preserving
placeholders (e.g., {name}) and the JSON keys: confirmationTitle,
confirmationQuestion, previewTitle, actions.view, actions.viewDescription,
actions.install, actions.installDescription, actions.discard,
actions.discardDescription, result.viewed, result.installed, result.discarded,
result.failed; for example use Polish equivalents like "Szkic umiejętności" for
confirmationTitle and "Wygenerowano szkic umiejętności: {name}" for
confirmationQuestion, and provide Polish texts for previewTitle ("Podgląd treści
szkicu"), actions.view ("Wyświetl treść"), actions.viewDescription ("Podgląd
treści szkicu umiejętności"), actions.install ("Zainstaluj jako umiejętność"),
actions.installDescription ("Zainstaluj szkic w katalogu umiejętności"),
actions.discard ("Usuń"), actions.discardDescription ("Usuń tymczasowy szkic"),
and result messages like "Szkic wyświetlony", "Szkic zainstalowany", "Szkic
usunięty", "Akcja na szkicu nie powiodła się" respectively.

---

Nitpick comments:
In `@src/renderer/src/i18n/zh-CN/chat.json`:
- Line 73: Move the "skillDraft" object in zh-CN chat.json from its current
position after the "input" section to follow the "onboarding" section so the key
ordering matches other locales; specifically locate the "skillDraft" key and
cut/paste the entire object to immediately after the "onboarding" key, adjust
surrounding commas to keep valid JSON, and run a quick JSON lint to confirm no
syntax errors.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 87476125-5229-49ca-91c2-40933936c2d4

📥 Commits

Reviewing files that changed from the base of the PR and between 8e8550b and 76daa16.

📒 Files selected for processing (45)
  • docs/features/skill-draft-confirmation-card/plan.md
  • docs/features/skill-draft-confirmation-card/spec.md
  • docs/features/skill-draft-confirmation-card/tasks.md
  • src/main/presenter/agentRuntimePresenter/dispatch.ts
  • src/main/presenter/agentRuntimePresenter/index.ts
  • src/main/presenter/agentRuntimePresenter/types.ts
  • src/main/presenter/skillPresenter/index.ts
  • src/main/presenter/toolPresenter/agentTools/agentToolManager.ts
  • src/main/routes/chat/chatService.ts
  • src/renderer/src/components/chat/ChatToolInteractionOverlay.vue
  • src/renderer/src/components/chat/messageListItems.ts
  • src/renderer/src/components/message/MessageBlockQuestionRequest.vue
  • src/renderer/src/i18n/da-DK/chat.json
  • src/renderer/src/i18n/de-DE/chat.json
  • src/renderer/src/i18n/en-US/chat.json
  • src/renderer/src/i18n/es-ES/chat.json
  • src/renderer/src/i18n/fa-IR/chat.json
  • src/renderer/src/i18n/fr-FR/chat.json
  • src/renderer/src/i18n/he-IL/chat.json
  • src/renderer/src/i18n/id-ID/chat.json
  • src/renderer/src/i18n/it-IT/chat.json
  • src/renderer/src/i18n/ja-JP/chat.json
  • src/renderer/src/i18n/ko-KR/chat.json
  • src/renderer/src/i18n/ms-MY/chat.json
  • src/renderer/src/i18n/pl-PL/chat.json
  • src/renderer/src/i18n/pt-BR/chat.json
  • src/renderer/src/i18n/ru-RU/chat.json
  • src/renderer/src/i18n/tr-TR/chat.json
  • src/renderer/src/i18n/vi-VN/chat.json
  • src/renderer/src/i18n/zh-CN/chat.json
  • src/renderer/src/i18n/zh-HK/chat.json
  • src/renderer/src/i18n/zh-TW/chat.json
  • src/renderer/src/pages/ChatPage.vue
  • src/shared/chat.d.ts
  • src/shared/contracts/common.ts
  • src/shared/types/agent-interface.d.ts
  • src/shared/types/core/chat.ts
  • src/shared/types/skill.ts
  • test/main/presenter/agentRuntimePresenter/agentRuntimePresenter.test.ts
  • test/main/presenter/agentRuntimePresenter/dispatch.test.ts
  • test/main/presenter/skillPresenter/skillPresenter.test.ts
  • test/main/presenter/toolPresenter/agentTools/agentToolManagerSettings.test.ts
  • test/renderer/components/ChatPage.test.ts
  • test/renderer/components/message/MessageBlockBasics.test.ts
  • tsconfig.node.tsbuildinfo

Comment on lines +416 to +435
function extractSkillDraftPromptPayload(
rawData: MCPToolResponse
): SkillDraftPromptPayload | undefined {
const toolResult = rawData.toolResult as SkillDraftToolResult | null | undefined
const skillDraft = toolResult?.skillDraft
if (!skillDraft || typeof skillDraft !== 'object') {
return undefined
}
if (skillDraft.status !== 'created') {
return undefined
}
if (typeof skillDraft.draftId !== 'string' || typeof skillDraft.skillName !== 'string') {
return undefined
}
const draftId = skillDraft.draftId.trim()
const skillName = skillDraft.skillName.trim()
if (!draftId || !skillName) {
return undefined
}
return { draftId, skillName }
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Only accept draft prompts from the expected tool origin.

This trusts any tool result that happens to expose toolResult.skillDraft, then turns it into a privileged local draft action flow. A buggy or untrusted MCP tool can spoof this shape and surface view/install/discard against an arbitrary draft id. Gate the extraction on the executed tool name/source before enqueueing the question.

Suggested fix
-function extractSkillDraftPromptPayload(
-  rawData: MCPToolResponse
-): SkillDraftPromptPayload | undefined {
+function extractSkillDraftPromptPayload(
+  toolName: string,
+  rawData: MCPToolResponse
+): SkillDraftPromptPayload | undefined {
+  if (toolName !== 'skill_manage') {
+    return undefined
+  }
   const toolResult = rawData.toolResult as SkillDraftToolResult | null | undefined
   const skillDraft = toolResult?.skillDraft
   if (!skillDraft || typeof skillDraft !== 'object') {
     return undefined
   }
@@
-        skillDraftPrompt: extractSkillDraftPromptPayload(toolRawData),
+        skillDraftPrompt: extractSkillDraftPromptPayload(completedToolCall.name, toolRawData),

Also applies to: 1058-1058

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/main/presenter/agentRuntimePresenter/dispatch.ts` around lines 416 - 435,
The extractor currently accepts any MCPToolResponse that contains
toolResult.skillDraft; restrict it to only trust responses from the
known/trusted skill-draft tool by checking the tool identity first (e.g.,
compare rawData.toolName or rawData.toolExecution.name/id against a single
trusted constant like SKILL_DRAFT_TOOL_NAME or an allowlist) before reading
toolResult.skillDraft; if the tool identity does not match, return undefined.
Apply the same guard in the other occurrence referenced (around the other
extract call at the later location) so only the trusted tool can trigger the
draft prompt flow.

Comment on lines 302 to 310
private readonly skillPresenter?: Pick<
ISkillPresenter,
'getMetadataList' | 'getActiveSkills' | 'loadSkillContent'
| 'getMetadataList'
| 'getActiveSkills'
| 'loadSkillContent'
| 'viewDraftSkill'
| 'installDraftSkill'
| 'discardDraftSkill'
>
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Don’t expose a draft-confirmation flow that depends on an optional port.

This PR can enqueue skill-draft confirmations, but the runtime still allows skillPresenter to be absent and then throws when the user clicks one of the draft actions. That leaves the message in a dead-end state instead of resolving the interaction cleanly. Make these draft methods required for this path, or short-circuit before the confirmation block is shown.

Also applies to: 325-333, 1011-1013

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/main/presenter/agentRuntimePresenter/index.ts` around lines 302 - 310,
The code exposes draft-confirmation actions through an optional skillPresenter
which can be undefined and cause runtime throws when a user triggers a draft
action; either make the draft methods required on skillPresenter or
short-circuit before showing/enqueuing the confirmation. Fix by updating the
presenter field or call sites that enqueue confirmations: ensure the private
readonly skillPresenter property includes non-optional 'viewDraftSkill',
'installDraftSkill', and 'discardDraftSkill' (so callers must supply them), or
add a guard in the confirmation/enqueue logic (check if !this.skillPresenter or
missing methods) and immediately resolve/return a clean error/disabled response
instead of displaying the confirmation UI. Update the same pattern where draft
actions are enqueued (the other occurrences referenced around the file) so every
draft-confirmation path checks skillPresenter presence before proceeding.

Comment on lines +2467 to +2477
private removeEmptyDraftConversationDir(conversationId: string): void {
const safeConversationId = this.validateDraftConversationId(conversationId)
if (!safeConversationId) {
return
}

const conversationDir = path.join(this.draftsRoot, safeConversationId)
if (fs.existsSync(conversationDir) && fs.readdirSync(conversationDir).length === 0) {
fs.rmSync(conversationDir, { recursive: true, force: true })
}
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Apply empty conversation-dir cleanup on manageDraftSkill('delete') as well.

removeEmptyDraftConversationDir is wired for install/discard, but delete still leaves empty per-conversation draft folders behind.

Suggested patch
         case 'delete': {
@@
           fs.rmSync(draftPath, { recursive: true, force: true })
+          this.removeEmptyDraftConversationDir(conversationId)
           return { success: true, action, draftId }
         }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/main/presenter/skillPresenter/index.ts` around lines 2467 - 2477, The
cleanup function removeEmptyDraftConversationDir currently runs for
install/discard flows but not when manageDraftSkill is invoked with action
'delete', leaving empty conversation folders; update the manageDraftSkill
handler (the function named manageDraftSkill and its 'delete' branch) to call
this.removeEmptyDraftConversationDir(conversationId) after the deletion
completes (same place it’s called for 'install'/'discard') so the
per-conversation draft directory is removed when empty.

Comment thread src/renderer/src/i18n/da-DK/chat.json
Comment thread src/renderer/src/i18n/de-DE/chat.json
Comment on lines +384 to +401
"skillDraft": {
"confirmationTitle": "Skill Draft",
"confirmationQuestion": "A skill draft has been generated: {name}",
"previewTitle": "Draft Content Preview",
"actions": {
"view": "View Content",
"viewDescription": "Preview the draft skill content",
"install": "Install as Skill",
"installDescription": "Install the draft into the skills directory",
"discard": "Discard",
"discardDescription": "Delete the temporary draft"
},
"result": {
"viewed": "Draft viewed",
"installed": "Draft installed",
"discarded": "Draft discarded",
"failed": "Draft action failed"
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Provide Spanish translations for the new skillDraft entries.

These strings are currently English, so the es-ES locale will show mixed-language content in the draft-confirmation flow.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/renderer/src/i18n/es-ES/chat.json` around lines 384 - 401, Translate the
English strings under the "skillDraft" key into Spanish: update
"confirmationTitle", "confirmationQuestion", "previewTitle", all entries under
"actions" (view, viewDescription, install, installDescription, discard,
discardDescription) and all entries under "result" (viewed, installed,
discarded, failed) so the es-ES locale is fully Spanish; keep placeholders like
{name} intact and use natural Spanish phrases (e.g., "Borrador de habilidad",
"Se ha generado un borrador: {name}", "Vista previa del contenido", "Ver
contenido", "Instalar como habilidad", "Descartar", "Acción de borrador
fallida", etc.) while preserving key names ("skillDraft" and nested keys)
exactly.

Comment thread src/renderer/src/i18n/pl-PL/chat.json
@zerob13 zerob13 merged commit 25f9c54 into dev May 28, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants