Compare commits

...

2 Commits

Author SHA1 Message Date
celestial-vault c58ff9bbff changeset 2025-04-17 16:18:09 -07:00
celestial-vault 6f4a0eae12 add a delete button to the cline rules modal 2025-04-17 16:17:36 -07:00
7 changed files with 94 additions and 3 deletions
+5
View File
@@ -0,0 +1,5 @@
---
"claude-dev": minor
---
Add a delete button to the Cline Rules modal to delete rule files
@@ -173,3 +173,49 @@ export async function refreshClineRulesToggles(
localToggles: updatedLocalToggles,
}
}
export async function deleteRuleFile(
context: vscode.ExtensionContext,
rulePath: string,
isGlobal: boolean,
): Promise<{ success: boolean; message: string }> {
try {
// Check if file exists
const fileExists = await fileExistsAtPath(rulePath)
if (!fileExists) {
return {
success: false,
message: `Rule file does not exist: ${rulePath}`,
}
}
// Delete the file from disk
await fs.unlink(rulePath)
// Get the filename for messages
const fileName = path.basename(rulePath)
// Update the appropriate toggles
if (isGlobal) {
const toggles = ((await getGlobalState(context, "globalClineRulesToggles")) as ClineRulesToggles) || {}
delete toggles[rulePath]
await updateGlobalState(context, "globalClineRulesToggles", toggles)
} else {
const toggles = ((await getWorkspaceState(context, "localClineRulesToggles")) as ClineRulesToggles) || {}
delete toggles[rulePath]
await updateWorkspaceState(context, "localClineRulesToggles", toggles)
}
return {
success: true,
message: `Rule file "${fileName}" deleted successfully`,
}
} catch (error) {
const errorMessage = error instanceof Error ? error.message : String(error)
console.error(`Error deleting rule file: ${errorMessage}`, error)
return {
success: false,
message: `Failed to delete rule file.`,
}
}
}
+19 -1
View File
@@ -49,7 +49,7 @@ import {
} from "../storage/state"
import { Task, cwd } from "../task"
import { ClineRulesToggles } from "../../shared/cline-rules"
import { refreshClineRulesToggles } from "../context/instructions/user-instructions/cline-rules"
import { deleteRuleFile, refreshClineRulesToggles } from "../context/instructions/user-instructions/cline-rules"
/*
https://github.com/microsoft/vscode-webview-ui-toolkit-samples/blob/main/default/weather-webview/src/providers/WeatherViewProvider.ts
@@ -634,6 +634,24 @@ export class Controller {
}
break
}
case "deleteClineRule": {
const { isGlobal, rulePath } = message
if (rulePath && typeof isGlobal === "boolean") {
const result = await deleteRuleFile(this.context, rulePath, isGlobal)
if (result.success) {
await refreshClineRulesToggles(this.context, cwd)
await this.postStateToWebview()
} else {
console.error("Failed to delete rule file:", result.message)
}
} else {
console.error("deleteClineRule: Missing or invalid parameters", {
rulePath,
isGlobal: typeof isGlobal === "boolean" ? isGlobal : `Invalid: ${typeof isGlobal}`,
})
}
break
}
case "requestTotalTasksSize": {
this.refreshTotalTasksSize()
break
+1
View File
@@ -82,6 +82,7 @@ export interface WebviewMessage {
| "toggleFavoriteModel"
| "grpc_request"
| "toggleClineRule"
| "deleteClineRule"
// | "relaunchChromeDebugMode"
text?: string
@@ -111,6 +111,7 @@ const ClineRulesToggleModal: React.FC = () => {
<RulesToggleList
rules={globalRules}
toggleRule={(rulePath, enabled) => toggleRule(true, rulePath, enabled)}
isGlobal={true}
listGap="small"
/>
</div>
@@ -121,6 +122,7 @@ const ClineRulesToggleModal: React.FC = () => {
<RulesToggleList
rules={localRules}
toggleRule={(rulePath, enabled) => toggleRule(false, rulePath, enabled)}
isGlobal={false}
listGap="small"
/>
</div>
@@ -4,8 +4,9 @@ import { VSCodeButton } from "@vscode/webview-ui-toolkit/react"
const RuleRow: React.FC<{
rulePath: string
enabled: boolean
isGlobal: boolean
toggleRule: (rulePath: string, enabled: boolean) => void
}> = ({ rulePath, enabled, toggleRule }) => {
}> = ({ rulePath, enabled, isGlobal, toggleRule }) => {
// Get the filename from the path for display
const displayName = rulePath.split("/").pop() || rulePath
@@ -16,6 +17,14 @@ const RuleRow: React.FC<{
})
}
const handleDeleteClick = () => {
vscode.postMessage({
type: "deleteClineRule",
rulePath: rulePath,
isGlobal: isGlobal,
})
}
return (
<div className="mb-2.5">
<div
@@ -58,6 +67,14 @@ const RuleRow: React.FC<{
style={{ height: "20px" }}>
<span className="codicon codicon-edit" style={{ fontSize: "14px" }} />
</VSCodeButton>
<VSCodeButton
appearance="icon"
aria-label="Delete rule file"
title="Delete rule file"
onClick={handleDeleteClick}
style={{ height: "20px" }}>
<span className="codicon codicon-trash" style={{ fontSize: "14px" }} />
</VSCodeButton>
</div>
</div>
</div>
@@ -3,10 +3,12 @@ import RuleRow from "./RuleRow"
const RulesToggleList = ({
rules,
toggleRule,
isGlobal,
listGap = "medium",
}: {
rules: [string, boolean][]
toggleRule: (rulePath: string, enabled: boolean) => void
isGlobal: boolean
listGap?: "small" | "medium" | "large"
}) => {
const gapClasses = {
@@ -20,7 +22,7 @@ const RulesToggleList = ({
return rules.length > 0 ? (
<div className={`flex flex-col ${gapClass}`}>
{rules.map(([rulePath, enabled]) => (
<RuleRow key={rulePath} rulePath={rulePath} enabled={enabled} toggleRule={toggleRule} />
<RuleRow key={rulePath} rulePath={rulePath} enabled={enabled} isGlobal={isGlobal} toggleRule={toggleRule} />
))}
</div>
) : (