Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ export { CredentialSelector } from './credential-selector/credential-selector'
export { DocumentSelector } from './document-selector/document-selector'
export { DocumentTagEntry } from './document-tag-entry/document-tag-entry'
export { Dropdown } from './dropdown/dropdown'
export { E2BSwitch } from './e2b-switch/e2b-switch'
export { EvalInput } from './eval-input/eval-input'
export { FileSelectorInput } from './file-selector/file-selector-input'
export { FileUpload } from './file-upload/file-upload'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ import {
DocumentSelector,
DocumentTagEntry,
Dropdown,
E2BSwitch,
EvalInput,
FileSelectorInput,
FileUpload,
Expand Down Expand Up @@ -291,18 +290,6 @@ function SubBlockComponent({
)

case 'switch':
if (config.id === 'remoteExecution') {
return (
<E2BSwitch
blockId={blockId}
subBlockId={config.id}
title={config.title ?? ''}
isPreview={isPreview}
previewValue={previewValue as any}
disabled={isDisabled}
/>
)
}
return (
<Switch
blockId={blockId}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ export function Panel() {
// Delete workflow hook
const { isDeleting, handleDeleteWorkflow } = useDeleteWorkflow({
workspaceId,
workflowId: activeWorkflowId || '',
getWorkflowIds: () => activeWorkflowId || '',
isActive: true,
onSuccess: () => setIsDeleteModalOpen(false),
})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,11 @@ interface ContextMenuProps {
* Callback when delete is clicked
*/
onDelete: () => void
/**
* Whether to show the rename option (default: true)
* Set to false when multiple items are selected
*/
showRename?: boolean
}

/**
Expand All @@ -45,6 +50,7 @@ export function ContextMenu({
onClose,
onRename,
onDelete,
showRename = true,
}: ContextMenuProps) {
return (
<Popover open={isOpen} onOpenChange={onClose}>
Expand All @@ -58,15 +64,17 @@ export function ContextMenu({
}}
/>
<PopoverContent ref={menuRef} align='start' side='bottom' sideOffset={4}>
<PopoverItem
onClick={() => {
onRename()
onClose()
}}
>
<Pencil className='h-3 w-3' />
<span>Rename</span>
</PopoverItem>
{showRename && (
<PopoverItem
onClick={() => {
onRename()
onClose()
}}
>
<Pencil className='h-3 w-3' />
<span>Rename</span>
</PopoverItem>
)}
<PopoverItem
onClick={() => {
onDelete()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,10 @@ interface DeleteModalProps {
*/
itemType: 'workflow' | 'folder'
/**
* Name of the item being deleted (optional, for display)
* Name(s) of the item(s) being deleted (optional, for display)
* Can be a single name or an array of names for multiple items
*/
itemName?: string
itemName?: string | string[]
}

/**
Expand All @@ -52,12 +53,37 @@ export function DeleteModal({
itemType,
itemName,
}: DeleteModalProps) {
const title = itemType === 'workflow' ? 'Delete workflow?' : 'Delete folder?'
const isMultiple = Array.isArray(itemName) && itemName.length > 1
const isSingle = !isMultiple

const description =
itemType === 'workflow'
? 'Deleting this workflow will permanently remove all associated blocks, executions, and configuration.'
: 'Deleting this folder will permanently remove all associated workflows, logs, and knowledge bases.'
const displayNames = Array.isArray(itemName) ? itemName : itemName ? [itemName] : []

let title = ''
if (itemType === 'workflow') {
title = isMultiple ? 'Delete workflows?' : 'Delete workflow?'
} else {
title = 'Delete folder?'
}

let description = ''
if (itemType === 'workflow') {
if (isMultiple) {
const workflowList = displayNames.join(', ')
description = `Deleting ${workflowList} will permanently remove all associated blocks, executions, and configuration.`
} else if (isSingle && displayNames.length > 0) {
description = `Deleting ${displayNames[0]} will permanently remove all associated blocks, executions, and configuration.`
} else {
description =
'Deleting this workflow will permanently remove all associated blocks, executions, and configuration.'
}
} else {
if (isSingle && displayNames.length > 0) {
description = `Deleting ${displayNames[0]} will permanently remove all associated workflows, logs, and knowledge bases.`
} else {
description =
'Deleting this folder will permanently remove all associated workflows, logs, and knowledge bases.'
}
}

return (
<Modal open={isOpen} onOpenChange={onClose}>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
'use client'

import { useCallback, useState } from 'react'
import { useCallback, useRef, useState } from 'react'
import clsx from 'clsx'
import Link from 'next/link'
import { useParams } from 'next/navigation'
import { createLogger } from '@/lib/logs/console/logger'
import { useDeleteWorkflow } from '@/app/workspace/[workspaceId]/w/hooks'
import { useFolderStore } from '@/stores/folders/store'
import { useWorkflowRegistry } from '@/stores/workflows/registry/store'
Expand All @@ -13,8 +12,6 @@ import { useContextMenu, useItemDrag, useItemRename } from '../../../../hooks'
import { ContextMenu } from '../context-menu/context-menu'
import { DeleteModal } from '../delete-modal/delete-modal'

const logger = createLogger('WorkflowItem')

interface WorkflowItemProps {
workflow: WorkflowMetadata
active: boolean
Expand All @@ -33,17 +30,37 @@ export function WorkflowItem({ workflow, active, level, onWorkflowClick }: Workf
const params = useParams()
const workspaceId = params.workspaceId as string
const { selectedWorkflows } = useFolderStore()
const { updateWorkflow } = useWorkflowRegistry()
const { updateWorkflow, workflows } = useWorkflowRegistry()
const isSelected = selectedWorkflows.has(workflow.id)

// Delete modal state
const [isDeleteModalOpen, setIsDeleteModalOpen] = useState(false)
const [workflowIdsToDelete, setWorkflowIdsToDelete] = useState<string[]>([])
const [deleteModalNames, setDeleteModalNames] = useState<string | string[]>('')

// Capture selection at right-click time (using ref to persist across renders)
const capturedSelectionRef = useRef<{
workflowIds: string[]
workflowNames: string | string[]
} | null>(null)

/**
* Handle opening the delete modal - uses pre-captured selection state
*/
const handleOpenDeleteModal = useCallback(() => {
// Use the selection captured at right-click time
if (capturedSelectionRef.current) {
setWorkflowIdsToDelete(capturedSelectionRef.current.workflowIds)
setDeleteModalNames(capturedSelectionRef.current.workflowNames)
setIsDeleteModalOpen(true)
}
}, [])

// Delete workflow hook
const { isDeleting, handleDeleteWorkflow } = useDeleteWorkflow({
workspaceId,
workflowId: workflow.id,
isActive: active,
getWorkflowIds: () => workflowIdsToDelete,
isActive: (workflowIds) => workflowIds.includes(params.workflowId as string),
onSuccess: () => setIsDeleteModalOpen(false),
})

Expand Down Expand Up @@ -79,10 +96,49 @@ export function WorkflowItem({ workflow, active, level, onWorkflowClick }: Workf
isOpen: isContextMenuOpen,
position,
menuRef,
handleContextMenu,
handleContextMenu: handleContextMenuBase,
closeMenu,
} = useContextMenu()

/**
* Handle right-click - ensure proper selection behavior and capture selection state
* If right-clicking on an unselected workflow, select only that workflow
* If right-clicking on a selected workflow with multiple selections, keep all selections
*/
const handleContextMenu = useCallback(
(e: React.MouseEvent) => {
// Check current selection state at time of right-click
const { selectedWorkflows: currentSelection, selectOnly } = useFolderStore.getState()
const isCurrentlySelected = currentSelection.has(workflow.id)

// If this workflow is not in the current selection, select only this workflow
if (!isCurrentlySelected) {
selectOnly(workflow.id)
}

// Capture the selection state at right-click time
const finalSelection = useFolderStore.getState().selectedWorkflows
const finalIsSelected = finalSelection.has(workflow.id)

const workflowIds =
finalIsSelected && finalSelection.size > 1 ? Array.from(finalSelection) : [workflow.id]

const workflowNames = workflowIds
.map((id) => workflows[id]?.name)
.filter((name): name is string => !!name)
Comment on lines +126 to +128
Copy link
Contributor

Choose a reason for hiding this comment

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

logic: potential issue: if some workflows don't have names (undefined), workflowNames could be empty, causing incorrect modal text. Should include fallback like "Untitled Workflow".

Prompt To Fix With AI
This is a comment left during a code review.
Path: apps/sim/app/workspace/[workspaceId]/w/components/sidebar/components-new/workflow-list/components/workflow-item/workflow-item.tsx
Line: 126:128

Comment:
**logic:** potential issue: if some workflows don't have names (undefined), `workflowNames` could be empty, causing incorrect modal text. Should include fallback like "Untitled Workflow".

How can I resolve this? If you propose a fix, please make it concise.


// Store in ref so it persists even if selection changes
capturedSelectionRef.current = {
workflowIds,
workflowNames: workflowNames.length > 1 ? workflowNames : workflowNames[0],
}

// If already selected with multiple selections, keep all selections
handleContextMenuBase(e)
},
[workflow.id, workflows, handleContextMenuBase]
)

// Rename hook
const {
isEditing,
Expand Down Expand Up @@ -197,7 +253,8 @@ export function WorkflowItem({ workflow, active, level, onWorkflowClick }: Workf
menuRef={menuRef}
onClose={closeMenu}
onRename={handleStartEdit}
onDelete={() => setIsDeleteModalOpen(true)}
onDelete={handleOpenDeleteModal}
showRename={selectedWorkflows.size <= 1}
/>

{/* Delete Confirmation Modal */}
Expand All @@ -207,7 +264,7 @@ export function WorkflowItem({ workflow, active, level, onWorkflowClick }: Workf
onConfirm={handleDeleteWorkflow}
isDeleting={isDeleting}
itemType='workflow'
itemName={workflow.name}
itemName={deleteModalNames}
/>
</>
)
Expand Down
Loading