Skip to content

Add project deletion from sidebar context menu#50

Merged
juliusmarminge merged 3 commits intomainfrom
codething/9493a863
Feb 16, 2026
Merged

Add project deletion from sidebar context menu#50
juliusmarminge merged 3 commits intomainfrom
codething/9493a863

Conversation

@juliusmarminge
Copy link
Copy Markdown
Member

@juliusmarminge juliusmarminge commented Feb 15, 2026

Summary

  • Add a project-level right-click context menu action (Delete) in the sidebar.
  • On delete, remove the project in Electron mode and clean up associated sessions/terminal history for that project's threads.
  • Add DELETE_PROJECT reducer support to remove the project, prune its threads, and reassign activeThreadId safely.
  • Add reducer test coverage for deleting a project and all associated threads.

Testing

  • Added unit test: apps/web/src/store.test.ts (deletes a project and all of its threads).
  • Not run: lint/tests were not executed in this context.

Open with Devin

Summary by CodeRabbit

  • New Features

    • Right-click project context menu to delete a project with confirmation; prevents deletion of non-empty projects and shows warning or error toasts as needed.
    • Removing a project also removes its associated threads and updates the active-thread selection.
  • Tests

    • Added a test validating project deletion, cleanup of associated threads, and active-thread selection behavior.

@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Feb 15, 2026

No actionable comments were generated in the recent review. 🎉


Walkthrough

Adds a project-level right-click context menu that confirms and invokes project deletion via the Electron API, prevents deleting projects that still have threads, shows toasts for warnings/errors, and dispatches a new DELETE_PROJECT action; the reducer removes the project and its threads and updates activeThreadId.

Changes

Cohort / File(s) Summary
Store layer
apps/web/src/store.ts
Adds DELETE_PROJECT action type and reducer case to remove the specified project, delete threads with matching projectId, and set activeThreadId to an existing thread or null.
UI integration
apps/web/src/components/Sidebar.tsx
Adds handleProjectContextMenu (useCallback) wired to project header onContextMenu: prevents default menu, checks for threads (warning toast if non-empty), confirms deletion, calls api.projects.remove, logs/shows error on failure, and dispatches DELETE_PROJECT on success.
Tests
apps/web/src/store.test.ts
Adds test "deletes a project and all of its threads" asserting project removal, associated thread cleanup, and activeThreadId update.

Sequence Diagram(s)

sequenceDiagram
    actor User
    participant Sidebar
    participant "Electron API" as API
    participant Store
    participant Toasts

    User->>Sidebar: Right-click project
    Sidebar->>User: Show context menu (Delete)
    User->>Sidebar: Select Delete
    Sidebar->>Sidebar: Check for project threads
    alt project has threads
        Sidebar->>Toasts: Show warning toast, abort
    else project empty or user confirms
        Sidebar->>User: Show confirmation
        User->>Sidebar: Confirm
        Sidebar->>API: api.projects.remove(projectId, coords)
        API-->>Sidebar: Success / Error
        alt Error
            Sidebar->>Toasts: Show error toast
        else Success
            Sidebar->>Store: Dispatch DELETE_PROJECT(projectId)
            Store->>Store: Remove project, remove threads, update activeThreadId
            Store-->>Sidebar: New state
        end
    end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

🚥 Pre-merge checks | ✅ 3 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 50.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The pull request title directly and concisely summarizes the main change: adding project deletion functionality accessible via a right-click context menu in the sidebar.
Merge Conflict Detection ✅ Passed ✅ No merge conflicts detected when merging into main

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

✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch codething/9493a863

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

@macroscopeapp
Copy link
Copy Markdown
Contributor

macroscopeapp bot commented Feb 15, 2026

Add project deletion from the sidebar context menu in components.Sidebar to remove a project and its threads when confirmed

Add right-click context menu on project headers in Sidebar.tsx that triggers DELETE_PROJECT; implement reducer handling in store.ts to remove the project, prune its threads, and recalc activeThreadId; add a test in store.test.ts verifying state updates.

📍Where to Start

Start with the handleProjectContextMenu callback in Sidebar.tsx, then review the DELETE_PROJECT case in the reducer in store.ts.


Macroscope summarized 4c49b8a.

@greptile-apps
Copy link
Copy Markdown

greptile-apps bot commented Feb 15, 2026

Greptile Summary

This PR adds project deletion functionality with proper safeguards and confirmation dialogs. The implementation prevents deletion of projects with active threads, requiring users to delete all threads first. The reducer properly handles thread cleanup and active thread reassignment when a project is deleted.

Key changes:

  • Added right-click context menu for projects with Delete action
  • Implemented validation that blocks deletion of non-empty projects with a warning toast
  • Added confirmation dialog before deletion (addresses previous review comment)
  • Electron mode properly calls api.projects.remove with error handling
  • DELETE_PROJECT reducer filters threads and safely reassigns activeThreadId
  • Added comprehensive unit test coverage

Code quality:

  • The reducer includes defensive thread cleanup logic even though the UI prevents deletion when threads exist - this is good defensive programming
  • Error handling is robust with try-catch blocks and user-facing error toasts
  • The active thread reassignment logic correctly handles edge cases (no remaining threads, deleted thread was active, etc.)

Confidence Score: 4/5

  • This PR is safe to merge with minimal risk - solid implementation with proper validation and error handling
  • Score reflects well-structured implementation with confirmation dialogs, validation to prevent data loss, comprehensive error handling, and good test coverage. Slightly below perfect due to the defensive thread cleanup code in the reducer that's technically unreachable through the UI flow, though this is actually beneficial defensive programming rather than a bug.
  • No files require special attention - all changes follow established patterns and include proper safeguards

Important Files Changed

Filename Overview
apps/web/src/components/Sidebar.tsx Adds project deletion with confirmation dialog and validation that prevents deleting non-empty projects
apps/web/src/store.ts Implements DELETE_PROJECT reducer with thread cleanup and safe active thread reassignment logic
apps/web/src/store.test.ts Adds comprehensive test coverage for project deletion including thread cleanup and active thread selection

Flowchart

flowchart TD
    A[User right-clicks project] --> B[Show context menu]
    B --> C{User clicks Delete?}
    C -->|No| Z[End]
    C -->|Yes| D[Find project by ID]
    D --> E{Project exists?}
    E -->|No| Z
    E -->|Yes| F[Check project threads]
    F --> G{Has threads?}
    G -->|Yes| H[Show warning toast]
    H --> I[Prevent deletion]
    I --> Z
    G -->|No| J[Show confirmation dialog]
    J --> K{User confirms?}
    K -->|No| Z
    K -->|Yes| L{isElectron?}
    L -->|Yes| M[Call api.projects.remove]
    M --> N{Success?}
    N -->|No| O[Show error toast]
    O --> Z
    N -->|Yes| P[Dispatch DELETE_PROJECT]
    L -->|No| P
    P --> Q[Filter out project]
    Q --> R[Filter out threads]
    R --> S[Reassign activeThreadId]
    S --> T[Return new state]
    T --> Z
Loading

Last reviewed commit: 4c49b8a

Copy link
Copy Markdown

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

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

3 files reviewed, 1 comment

Edit Code Review Agent Settings | Greptile

Comment on lines +325 to +340
const handleProjectContextMenu = useCallback(
async (projectId: string, position: { x: number; y: number }) => {
if (!api) return;
const clicked = await api.contextMenu.show([{ id: "delete", label: "Delete" }], position);
if (clicked !== "delete") return;

const project = state.projects.find((entry) => entry.id === projectId);
if (!project) return;

if (isElectron) {
try {
await api.projects.remove({ id: projectId });
} catch {
return;
}
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Missing confirmation dialog before deleting project. Thread deletion (line 278) uses api.dialogs.confirm to warn users - project deletion should too since it's more destructive (deletes all threads)

Copy link
Copy Markdown

@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: 2

🤖 Fix all issues with AI agents
In `@apps/web/src/components/Sidebar.tsx`:
- Around line 334-340: The current deletion path in Sidebar.tsx silently returns
on api.projects.remove failure (inside the isElectron branch) leaving the user
without feedback; update the try/catch around api.projects.remove to catch the
error, log it, and surface a user-visible notification (e.g., show an error
dialog or toast via your existing UI notification utility) that the project
deletion failed and include the error message; ensure you do not proceed with
local UI state changes (e.g., any code that removes the project from state or
navigation) when the backend delete fails so the UI remains consistent with the
backend.
- Around line 325-369: handleProjectContextMenu currently deletes project
threads but omits the worktree cleanup present in handleThreadContextMenu;
before closing terminals/stopping sessions for each thread inside
handleProjectContextMenu, detect any thread.worktree (e.g. thread.worktree?.path
or thread.worktreeId used in your code) and call the existing
removeWorktreeMutation with the appropriate identifier/path to remove the
on-disk worktree, awaiting it and swallowing expected errors like the
thread-level logic does; also add removeWorktreeMutation to the hook dependency
array for handleProjectContextMenu so the linting and behavior remain correct.
🧹 Nitpick comments (1)
apps/web/src/components/Sidebar.tsx (1)

325-332: Consider adding a confirmation dialog before deleting a project.

Deleting a project removes all associated threads and their data. Unlike thread deletion (which confirms before removing worktrees), project deletion proceeds immediately after the context menu click. This is a destructive action that could benefit from a confirmation step.

💬 Suggested confirmation dialog
       const project = state.projects.find((entry) => entry.id === projectId);
       if (!project) return;
 
+      const threadCount = state.threads.filter((t) => t.projectId === projectId).length;
+      const confirmed = await api.dialogs.confirm(
+        `Delete project "${project.name}" and its ${threadCount} thread(s)?`
+      );
+      if (!confirmed) return;
+
       if (isElectron) {

Comment thread apps/web/src/components/Sidebar.tsx
Comment thread apps/web/src/components/Sidebar.tsx
- Add project right-click Delete action in `Sidebar` and clean up sessions/terminals before removal
- Add `DELETE_PROJECT` reducer action to remove the project, its threads, and reset active thread
- Add reducer test coverage for project deletion behavior
- Prompt before deleting a project with thread and linked worktree counts
- Best-effort remove orphaned worktrees when project threads are deleted
- Show toast with error details if project deletion fails
- Show warning toast when attempting to delete a non-empty project
- Simplify confirmation copy to emphasize irreversible deletion
- Remove thread/worktree/session cleanup from project delete flow
@juliusmarminge
Copy link
Copy Markdown
Member Author

@greptileai review

@juliusmarminge juliusmarminge merged commit 748ea2a into main Feb 16, 2026
4 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.

1 participant