diff --git a/apps/docs/content/docs/en/blocks/router.mdx b/apps/docs/content/docs/en/blocks/router.mdx index 44bac918e7..a9d4d008df 100644 --- a/apps/docs/content/docs/en/blocks/router.mdx +++ b/apps/docs/content/docs/en/blocks/router.mdx @@ -2,7 +2,6 @@ title: Router --- -import { Callout } from 'fumadocs-ui/components/callout' import { Tab, Tabs } from 'fumadocs-ui/components/tabs' import { Image } from '@/components/ui/image' @@ -102,11 +101,18 @@ Input (Lead) → Router └── [Self-serve] → Workflow (Automated Onboarding) ``` +## Error Handling + +When the Router cannot determine an appropriate route for the given context, it will route to the **error path** instead of arbitrarily selecting a route. This happens when: + +- The context doesn't clearly match any of the defined route descriptions +- The AI determines that none of the available routes are appropriate + ## Best Practices - **Write clear route descriptions**: Each route description should clearly explain when that route should be selected. Be specific about the criteria. - **Make routes mutually exclusive**: When possible, ensure route descriptions don't overlap to prevent ambiguous routing decisions. -- **Include an error/fallback route**: Add a catch-all route for unexpected inputs that don't match other routes. +- **Connect an error path**: Handle cases where no route matches by connecting an error handler for graceful fallback behavior. - **Use descriptive route titles**: Route titles appear in the workflow canvas, so make them meaningful for readability. - **Test with diverse inputs**: Ensure the Router handles various input types, edge cases, and unexpected content. - **Monitor routing performance**: Review routing decisions regularly and refine route descriptions based on actual usage patterns. diff --git a/apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/editor/components/sub-block/components/condition-input/condition-input.tsx b/apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/editor/components/sub-block/components/condition-input/condition-input.tsx index 04558ef969..27232889b6 100644 --- a/apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/editor/components/sub-block/components/condition-input/condition-input.tsx +++ b/apps/sim/app/workspace/[workspaceId]/w/[workflowId]/components/panel/components/editor/components/sub-block/components/condition-input/condition-input.tsx @@ -654,17 +654,20 @@ export function ConditionInput({ } const removeBlock = (id: string) => { - if (isPreview || disabled || conditionalBlocks.length <= 2) return + if (isPreview || disabled) return + // Condition mode requires at least 2 blocks (if/else), router mode requires at least 1 + const minBlocks = isRouterMode ? 1 : 2 + if (conditionalBlocks.length <= minBlocks) return // Remove any associated edges before removing the block + const handlePrefix = isRouterMode ? `router-${id}` : `condition-${id}` const edgeIdsToRemove = edges - .filter((edge) => edge.sourceHandle?.startsWith(`condition-${id}`)) + .filter((edge) => edge.sourceHandle?.startsWith(handlePrefix)) .map((edge) => edge.id) if (edgeIdsToRemove.length > 0) { batchRemoveEdges(edgeIdsToRemove) } - if (conditionalBlocks.length === 1) return shouldPersistRef.current = true setConditionalBlocks((blocks) => updateBlockTitles(blocks.filter((block) => block.id !== id))) @@ -816,7 +819,9 @@ export function ConditionInput({