Skip to content

Improve flow builder canvas interactions - #4053

Merged
DonOmalVindula merged 1 commit into
thunder-id:mainfrom
DonOmalVindula:flow-builder-canvas-ux
Jul 20, 2026
Merged

Improve flow builder canvas interactions#4053
DonOmalVindula merged 1 commit into
thunder-id:mainfrom
DonOmalVindula:flow-builder-canvas-ux

Conversation

@DonOmalVindula

@DonOmalVindula DonOmalVindula commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Purpose

Improve the flow builder canvas and properties panel UX. This addresses the canvas interaction gaps listed in #3871 (follow-up to #4015) plus a set of consistency and discoverability issues found along the way:

Canvas nodes

  • Step headers now show the step id as the title (the executor/view type is already conveyed by the node body). Double-clicking the header edits the id inline, with validation (charset + uniqueness) and full edge rewiring (source/target endpoints and {id}_NEXT / {id}_INCOMPLETE handles).
  • Step id edits stay in sync between the node header and the properties panel Id field; both route through a shared useRenameStep hook. The panel Id field previously wrote into node data, which the save transformer ignored.
  • Executor nodes and the resource panel now render icon, title, and description from the same executor metadata via a shared ResourceDisplayImage component (asset paths and icon-library names). The Google/GitHub special-case renderers, which had drifted from the panel entries, are removed.
  • Node descriptions moved out of node bodies into a header hint icon that reveals the description in a tooltip on hover.
  • Header background unified to #151515 with step id at font weight 600.
  • Google entries use the full-color Google logo everywhere, with a new preserveImageColor display flag so dark mode does not invert full-color brand logos. Monochrome button icons inside view nodes (e.g. GitHub) now invert correctly in dark mode.
  • Call nodes created by the Self Sign Up / Sign In / Recovery link widgets get purposeful id prefixes so they are distinguishable.
  • Edge delete button also appears while the edge is selected (previously hover-only).
  • Composite execution nodes: the header Cog button now opens the executor properties (it previously did nothing), and a single click on the header selects the step - replacing the undocumented double-click gesture. Pointer cursors added on clickable node content.
  • Each view node header has a preview (eye) button that opens the end-user flow preview focused directly at that screen (startAt on the simulation).
  • Entering the preview collapses the resource and properties panels so the preview gets the full width.

Properties panel

  • Executor checkbox options render with the hint as a small caption underneath (matching the application edit page pattern) instead of full-width helper paragraphs; verbose intro text removed.
  • Action buttons (Delete, Add class, Add Input, Add new translation) unified via a shared PanelActionButton styled like the flow preview's option rows.
  • Id fields no longer show the dynamic/i18n value adornment (ids are identifiers, not display text).
  • Panel heading icon matches the node header cog.

Notifications panel

  • Notification entries are now clickable severity-bordered rows (whole-row click navigates to the offending resource) instead of alert boxes with underlined "Show" links; tabs show colored severity icons and count pills; empty tabs show a friendly success state.

Misc

  • SessionExecutor panel entry gained its missing description.
  • Node properties persist for all step types in the save transformer.

Approach

  • Node ids are the semantic identity in the flow definition, so renaming rewires edges rather than storing a cosmetic name; a shared hook (useRenameStep) keeps every rename surface consistent and syncs the interaction state.
  • Panel/canvas display metadata comes from the single executor definition source; rendering is unified in ResourceDisplayImage so the two surfaces cannot drift again.
  • The per-screen preview reuses the existing flow preview machinery (useFlowSimulation) with a new startAt entry point, exposed to canvas nodes through a minimal context carrying only a stable callback.

Related Issues

Related PRs

Checklist

  • Followed the contribution guidelines.
  • Manual test round performed and verified.
  • Documentation provided. (Add links if there are any)
    • Ran Vale and fixed all errors and warnings
  • Tests provided. (Add links if there are any)
    • Unit Tests
    • Integration Tests
  • Breaking changes. (Fill if applicable)
    • Breaking changes section filled.
    • breaking change label added.

Security checks

  • Followed secure coding standards in WSO2 Secure Coding Guidelines
  • Confirmed that this PR doesn't commit any keys, passwords, tokens, usernames, or other secrets.

Summary by CodeRabbit

  • New Features
    • Rename flow steps directly from their headers, with validation and automatic connection updates.
    • Preview individual flow steps from the canvas.
    • Added clearer resource icons/descriptions and improved dark-mode brand image handling.
    • Added compact, consistent action controls throughout property panels.
  • Bug Fixes
    • Kept edge deletion controls visible when selected.
    • Improved field error messages and execution-step/panel interactions.
    • Improved validation notifications navigation and count badges.
  • Style
    • Login-flow routes now use a collapsed sidebar for more workspace.

@coderabbitai

coderabbitai Bot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

The PR adds inline step renaming and node-focused preview simulation, centralizes resource image rendering, updates property-panel controls and validation handling, persists node properties and generated ID prefixes, and refreshes validation-panel, sidebar, edge, and route behavior.

Changes

Flow builder interactions

Layer / File(s) Summary
Step preview and selection
frontend/apps/console/src/features/flows/{hooks,context,components}/...
Adds node-focused simulation preview, click-based action-panel selection, preview controls, and panel closing during simulation.
Step ID renaming
frontend/apps/console/src/features/flows/hooks/useRenameStep.ts, .../resources/steps/StepTitle.tsx, .../resource-property-panel/ResourceProperties.tsx
Supports validated inline step renaming and rewires related nodes, edges, handles, and interaction state.
Display metadata rendering
frontend/apps/console/src/features/flows/components/ResourceDisplayImage.tsx, .../execution/execution-factory/*, .../resources/elements/adapters/ButtonAdapter.tsx
Centralizes asset/icon rendering, preserves selected brand colors, and updates executor display fallbacks and dark-mode icon handling.

Property panels and persisted metadata

Layer / File(s) Summary
Property-panel controls and errors
frontend/apps/console/src/features/flows/components/resource-property-panel/*, frontend/apps/console/src/features/login-flow/components/resource-property-panel/...
Adds shared field-error lookup, standardized panel action buttons, deferred step-ID commits, checkbox hints, and updated executor property controls.
Node properties and generated IDs
frontend/apps/console/src/features/flows/models/*, frontend/apps/console/src/features/flows/utils/*, frontend/apps/console/src/features/login-flow/data/*
Persists arbitrary node properties and allows configured prefixes for generated ID placeholders.

Validation and layout

Layer / File(s) Summary
Validation and navigation presentation
frontend/apps/console/src/features/flows/components/validation-panel/*
Reworks notification rows, adds severity counts, and bounds single-node fitView zoom.
Layout and edge controls
frontend/apps/console/src/App.tsx, frontend/apps/console/src/layouts/DashboardLayout.tsx, frontend/apps/console/src/features/flows/components/react-flow-overrides/*
Adds collapsible sidebars for flow routes and keeps selected-edge delete controls visible at a larger size.

Estimated code review effort: 4 (Complex) | ~60 minutes

Possibly related PRs

  • thunder-id/thunderid#3859: Both changes touch ClassesPropertyField.tsx; this PR standardizes its add-class action with PanelActionButton.
  • thunder-id/thunderid#4015: Both changes touch flow simulation and preview wiring through useFlowSimulation.ts and DecoratedVisualFlow.tsx.

Suggested reviewers: jeradrutnam, brionmario

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title is concise and accurately captures the broad flow builder canvas interaction improvements.
Description check ✅ Passed The description includes the required Purpose, Approach, Issues, PRs, checklist, and security sections with sufficient detail.
Docstring Coverage ✅ Passed Docstring coverage is 90.00% which is sufficient. The required threshold is 80.00%.
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.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

frontend/apps/console/src/App.tsx

ESLint skipped: missing config or dependency (missing-dependency). The ESLint configuration references a package that is not available in the sandbox.

frontend/apps/console/src/features/flows/components/ResourceDisplayImage.tsx

ESLint skipped: the ESLint configuration for this file references a package that is not available in the sandbox.

frontend/apps/console/src/features/flows/components/react-flow-overrides/BaseEdge.tsx

ESLint skipped: the ESLint configuration for this file references a package that is not available in the sandbox.

  • 65 others

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.

@DonOmalVindula
DonOmalVindula force-pushed the flow-builder-canvas-ux branch 2 times, most recently from c820d88 to 19850a7 Compare July 16, 2026 08:10
@DonOmalVindula
DonOmalVindula force-pushed the flow-builder-canvas-ux branch 5 times, most recently from c113b18 to b8dd2a2 Compare July 20, 2026 05:57

@coderabbitai coderabbitai Bot left a comment

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.

Actionable comments posted: 3

🧹 Nitpick comments (5)
frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx (2)

227-252: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Preview button duplicates the hover sx object a 5th time in this file.

The preview IconButton's sx (color/hover applyStyles block) is an exact copy of the Add/Configure/Delete buttons below it. Worth extracting into a shared constant (similar to the existing dashedAddButtonSx) to avoid drifting styles across five near-identical buttons.

🤖 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
`@frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx`
around lines 227 - 252, Extract the duplicated preview/Add/Configure/Delete
IconButton styling into a shared constant, analogous to dashedAddButtonSx, and
replace the inline sx object in the preview button and matching buttons below
with that constant. Preserve the existing color and light/dark hover behavior.

205-226: 🎯 Functional Correctness | 🔵 Trivial | ⚡ Quick win

New clickable header lacks keyboard support.

The header Box now has onClick + cursor: pointer to open the properties panel, but it's a plain div with no role, tabIndex, or key handler — keyboard users can't trigger this new shortcut (though the Cog/Configure button remains a keyboard-accessible fallback).

♻️ Suggested fix
       <Box
         data-testid="step-action-panel"
         display="flex"
         justifyContent="space-between"
         alignItems="center"
+        role={onActionPanelClick ? 'button' : undefined}
+        tabIndex={onActionPanelClick ? 0 : undefined}
         onClick={(event: MouseEvent<HTMLDivElement>) => {
           if ((event.target as HTMLElement).closest('button, input')) {
             return;
           }
           onActionPanelClick?.(event);
         }}
+        onKeyDown={(event: KeyboardEvent<HTMLDivElement>) => {
+          if ((event.key === 'Enter' || event.key === ' ') && !(event.target as HTMLElement).closest('button, input')) {
+            onActionPanelClick?.(event as unknown as MouseEvent<HTMLDivElement>);
+          }
+        }}
🤖 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
`@frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx`
around lines 205 - 226, Update the step-action-panel Box to be keyboard
accessible when onActionPanelClick is provided: add an appropriate interactive
role and tabIndex, and invoke the same onActionPanelClick behavior for Enter and
Space key presses while preserving the existing button/input exclusion for
pointer clicks.
frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.tsx (1)

107-118: 🎯 Functional Correctness | 🔵 Trivial | ⚡ Quick win

Description hint icon isn't reachable via keyboard.

The Tooltip wraps a plain Box (a div), which never receives focus, so the description tooltip can only be revealed by hovering with a mouse — keyboard-only users have no way to see it since there's no other UI surfacing displayDescription.

♻️ Suggested fix
             <Tooltip title={displayDescription}>
-              <Box
-                display="inline-flex"
-                alignItems="center"
+              <IconButton
+                size="small"
+                disableRipple
                 data-testid="execution-description-hint"
-                sx={{color: 'common.white', cursor: 'help', px: 0.5}}
+                sx={{color: 'common.white', cursor: 'help', p: 0.5}}
               >
                 <InfoIcon size={18} />
-              </Box>
+              </IconButton>
             </Tooltip>
🤖 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
`@frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.tsx`
around lines 107 - 118, Make the description hint in ExecutionMinimal
keyboard-reachable by replacing the non-focusable Box trigger around InfoIcon
with an appropriate focusable interactive element, while preserving the existing
tooltip, styling, test id, and displayDescription condition. Ensure the tooltip
opens when the element receives keyboard focus as well as on pointer hover.
frontend/apps/console/src/features/flows/components/resources/elements/adapters/ButtonAdapter.tsx (1)

30-34: 📐 Maintainability & Code Quality | 🔵 Trivial | 🏗️ Heavy lift

Hardcoded filename allowlist duplicates the preserveImageColor concept used elsewhere in this PR.

FULL_COLOR_ICON_PATTERN is a second, filename-based mechanism for "keep this icon's colors" alongside the metadata-driven display.preserveImageColor field already introduced in Execution.tsx/ExecutionFactory.tsx. Any new full-color icon added to widgets.json/executors.json later must remember to update this regex or it will get silently inverted in dark mode. Consider threading a preserveIconColor-style flag through ButtonConfig/ButtonElement instead, reusing the same convention.

Please also verify that the raw src values passed to renderButtonIcon (e.g. from buttonElement.startIcon) are never hashed/versioned by the asset pipeline before reaching resolveStaticResourcePath, since the $-anchored regex would silently stop matching if they were.

Also applies to: 120-133

🤖 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
`@frontend/apps/console/src/features/flows/components/resources/elements/adapters/ButtonAdapter.tsx`
around lines 30 - 34, Replace the filename-based FULL_COLOR_ICON_PATTERN logic
in ButtonAdapter/renderButtonIcon with a preserveIconColor-style flag propagated
through ButtonConfig and ButtonElement, sourced from the existing
display.preserveImageColor metadata used by Execution.tsx and
ExecutionFactory.tsx. Ensure renderButtonIcon passes raw src values unchanged to
resolveStaticResourcePath, without hashing or versioning, and use the propagated
flag to decide whether dark-mode inversion is applied.
frontend/apps/console/src/features/flows/utils/reactFlowTransformer.ts (1)

587-590: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Remove redundant property assignment.

This block can safely be removed. The mapping of stepData.properties to flowNode.properties is now universally handled at the top of the function (lines 508-512) for all node types, making this node-specific assignment redundant.

♻️ Proposed refactor
-    // Add decision properties if present (for conditions)
-    if (stepData?.properties && Object.keys(stepData.properties).length > 0) {
-      flowNode.properties = stepData.properties;
-    }
🤖 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 `@frontend/apps/console/src/features/flows/utils/reactFlowTransformer.ts`
around lines 587 - 590, Remove the conditional stepData.properties assignment
block from the node transformation logic. The existing universal mapping near
the start of the transformer should remain the sole source for assigning
flowNode.properties across all node types.
🤖 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
`@frontend/apps/console/src/features/flows/components/resource-property-panel/TextPropertyField.tsx`:
- Around line 157-162: Update the onBlur handler in TextPropertyField so the
commitsOnBlur path calls onChange without immediately resetting localValue; rely
on the existing propertyValue synchronization effect for successful updates. Add
a strict equality check to avoid invoking onChange when localValue already
equals propertyValue, preserving unchanged values on focus-and-blur.

In
`@frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.scss`:
- Around line 133-143: In the execution step styling block, add a blank line
between the padding declaration and the double-slash comment preceding cursor:
pointer to satisfy the scss/double-slash-comment-empty-line-before rule; leave
the hover styles unchanged.

In
`@frontend/apps/console/src/features/flows/components/resources/steps/StepTitle.tsx`:
- Around line 118-132: Update StepTitle’s rendered edit affordances so editing
is enabled only when stepId is available: guard the onDoubleClick handler, hide
or disable the rename Tooltip, and use a non-text cursor when stepId is null.
Preserve the existing displayed text while preventing palette/non-node instances
from entering the unsaveable edit state.

---

Nitpick comments:
In
`@frontend/apps/console/src/features/flows/components/resources/elements/adapters/ButtonAdapter.tsx`:
- Around line 30-34: Replace the filename-based FULL_COLOR_ICON_PATTERN logic in
ButtonAdapter/renderButtonIcon with a preserveIconColor-style flag propagated
through ButtonConfig and ButtonElement, sourced from the existing
display.preserveImageColor metadata used by Execution.tsx and
ExecutionFactory.tsx. Ensure renderButtonIcon passes raw src values unchanged to
resolveStaticResourcePath, without hashing or versioning, and use the propagated
flag to decide whether dark-mode inversion is applied.

In
`@frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.tsx`:
- Around line 107-118: Make the description hint in ExecutionMinimal
keyboard-reachable by replacing the non-focusable Box trigger around InfoIcon
with an appropriate focusable interactive element, while preserving the existing
tooltip, styling, test id, and displayDescription condition. Ensure the tooltip
opens when the element receives keyboard focus as well as on pointer hover.

In
`@frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx`:
- Around line 227-252: Extract the duplicated preview/Add/Configure/Delete
IconButton styling into a shared constant, analogous to dashedAddButtonSx, and
replace the inline sx object in the preview button and matching buttons below
with that constant. Preserve the existing color and light/dark hover behavior.
- Around line 205-226: Update the step-action-panel Box to be keyboard
accessible when onActionPanelClick is provided: add an appropriate interactive
role and tabIndex, and invoke the same onActionPanelClick behavior for Enter and
Space key presses while preserving the existing button/input exclusion for
pointer clicks.

In `@frontend/apps/console/src/features/flows/utils/reactFlowTransformer.ts`:
- Around line 587-590: Remove the conditional stepData.properties assignment
block from the node transformation logic. The existing universal mapping near
the start of the transformer should remain the sole source for assigning
flowNode.properties across all node types.
🪄 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: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: d477b44e-f89f-44fd-8245-6464ce3221fd

📥 Commits

Reviewing files that changed from the base of the PR and between 937116d and b8dd2a2.

📒 Files selected for processing (76)
  • frontend/apps/console/src/App.tsx
  • frontend/apps/console/src/features/flows/components/ResourceDisplayImage.tsx
  • frontend/apps/console/src/features/flows/components/react-flow-overrides/BaseEdge.tsx
  • frontend/apps/console/src/features/flows/components/react-flow-overrides/__tests__/BaseEdge.test.tsx
  • frontend/apps/console/src/features/flows/components/resource-panel/ResourcePanelItem.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/CheckboxPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ClassesPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/I18nConfigurationCard.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/PanelActionButton.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ResourceProperties.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ResourcePropertyPanel.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/TextPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/VariantSelect.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/__tests__/ResourcePropertyPanel.test.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/rich-text/RichTextWithTranslation.tsx
  • frontend/apps/console/src/features/flows/components/resources/elements/adapters/ButtonAdapter.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/StepTitle.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/__tests__/StepTitle.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/call/Call.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/call/__tests__/Call.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/Execution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.scss
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/__tests__/Execution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/__tests__/ExecutionMinimal.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/ExecutionFactory.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GithubExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GoogleExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/__tests__/ExecutionFactory.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/__tests__/GithubExecution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/__tests__/GoogleExecution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/ReorderableElement.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/__tests__/View.test.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/ValidationNotificationsList.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/ValidationPanel.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/__tests__/ValidationPanel.test.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/DecoratedVisualFlow.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/__tests__/DecoratedVisualFlow.test.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/__tests__/SimulationStepPreview.test.tsx
  • frontend/apps/console/src/features/flows/context/FlowBuilderCoreProvider.tsx
  • frontend/apps/console/src/features/flows/context/StepPreviewContext.tsx
  • frontend/apps/console/src/features/flows/context/__tests__/FlowBuilderCoreProvider.test.tsx
  • frontend/apps/console/src/features/flows/hooks/useFlowSimulation.ts
  • frontend/apps/console/src/features/flows/hooks/useRenameStep.ts
  • frontend/apps/console/src/features/flows/hooks/useResourceFieldError.ts
  • frontend/apps/console/src/features/flows/hooks/useStepPreview.ts
  • frontend/apps/console/src/features/flows/models/base.ts
  • frontend/apps/console/src/features/flows/models/steps.ts
  • frontend/apps/console/src/features/flows/utils/__tests__/reactFlowTransformer.test.ts
  • frontend/apps/console/src/features/flows/utils/__tests__/resolveStepMetadata.test.ts
  • frontend/apps/console/src/features/flows/utils/__tests__/updateTemplatePlaceholderReferences.test.ts
  • frontend/apps/console/src/features/flows/utils/reactFlowTransformer.ts
  • frontend/apps/console/src/features/flows/utils/updateTemplatePlaceholderReferences.ts
  • frontend/apps/console/src/features/login-flow/components/LoginFlowBuilder.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/CallProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/FieldExtendedProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/__tests__/ExecutionExtendedProperties.test.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/CheckboxWithHint.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/EmailProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/ExecutorInputsEditor.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/FederationProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/HttpRequestProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OUExecutorProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OUResolverProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OpenID4VPProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OtpProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/PermissionValidatorProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/ProvisioningProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/SmsProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/UserTypeResolverProperties.tsx
  • frontend/apps/console/src/features/login-flow/data/executors.json
  • frontend/apps/console/src/features/login-flow/data/templates.json
  • frontend/apps/console/src/features/login-flow/data/widgets.json
  • frontend/apps/console/src/layouts/DashboardLayout.tsx
  • frontend/packages/i18n/src/locales/en-US.ts
💤 Files with no reviewable changes (4)
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/tests/GithubExecution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GoogleExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GithubExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/tests/GoogleExecution.test.tsx

- Show the step id as the node header title with double-click-to-edit, including uniqueness and format validation and automatic edge rewiring
- Label the call nodes created by the sign-up, sign-in, and recovery link widgets with their purpose (icon, name, and description matching the resource panel entry) and purposeful id prefixes, so the otherwise identical nodes are tellable apart
- Persist node properties for every node type when saving, not only executions
- Keep the edge delete button visible while an edge is selected and enlarge its hit target
- Signal clickable step bodies and elements with pointer cursors and a hover tint

Refs thunder-id#3871
@DonOmalVindula
DonOmalVindula force-pushed the flow-builder-canvas-ux branch from b8dd2a2 to b922612 Compare July 20, 2026 06:21

@coderabbitai coderabbitai Bot left a comment

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.

🧹 Nitpick comments (1)
frontend/apps/console/src/features/flows/components/validation-panel/ValidationNotificationsList.tsx (1)

134-151: 🩺 Stability & Availability | 🔵 Trivial | ⚡ Quick win

Generic aria-label on notification rows.

Every navigable row announces the same aria-label={t('common:show')} regardless of content, giving screen-reader users no way to distinguish which notification a given row corresponds to.

♿ Proposed fix to make the aria-label content-aware
-            aria-label={t('common:show')}
+            aria-label={typeof notification.getMessage() === 'string' ? (notification.getMessage() as string) : t('common:show')}
🤖 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
`@frontend/apps/console/src/features/flows/components/validation-panel/ValidationNotificationsList.tsx`
around lines 134 - 151, Update the notification row rendered in
ValidationNotificationsList to derive its aria-label from the specific
notification content instead of the generic t('common:show') label. Reuse the
notification’s existing display text or accessible content so screen readers can
distinguish rows, while preserving the current onNotificationClick behavior and
styling.
🤖 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.

Nitpick comments:
In
`@frontend/apps/console/src/features/flows/components/validation-panel/ValidationNotificationsList.tsx`:
- Around line 134-151: Update the notification row rendered in
ValidationNotificationsList to derive its aria-label from the specific
notification content instead of the generic t('common:show') label. Reuse the
notification’s existing display text or accessible content so screen readers can
distinguish rows, while preserving the current onNotificationClick behavior and
styling.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 6d35bcc7-60aa-4f41-8207-1fa903be3b72

📥 Commits

Reviewing files that changed from the base of the PR and between b8dd2a2 and b922612.

📒 Files selected for processing (76)
  • frontend/apps/console/src/App.tsx
  • frontend/apps/console/src/features/flows/components/ResourceDisplayImage.tsx
  • frontend/apps/console/src/features/flows/components/react-flow-overrides/BaseEdge.tsx
  • frontend/apps/console/src/features/flows/components/react-flow-overrides/__tests__/BaseEdge.test.tsx
  • frontend/apps/console/src/features/flows/components/resource-panel/ResourcePanelItem.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/CheckboxPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ClassesPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/I18nConfigurationCard.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/PanelActionButton.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ResourceProperties.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ResourcePropertyPanel.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/TextPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/VariantSelect.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/__tests__/ResourcePropertyPanel.test.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/rich-text/RichTextWithTranslation.tsx
  • frontend/apps/console/src/features/flows/components/resources/elements/adapters/ButtonAdapter.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/StepTitle.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/__tests__/StepTitle.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/call/Call.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/call/__tests__/Call.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/Execution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.scss
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/__tests__/Execution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/__tests__/ExecutionMinimal.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/ExecutionFactory.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GithubExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GoogleExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/__tests__/ExecutionFactory.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/__tests__/GithubExecution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/__tests__/GoogleExecution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/ReorderableElement.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/__tests__/View.test.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/ValidationNotificationsList.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/ValidationPanel.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/__tests__/ValidationPanel.test.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/DecoratedVisualFlow.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/__tests__/DecoratedVisualFlow.test.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/__tests__/SimulationStepPreview.test.tsx
  • frontend/apps/console/src/features/flows/context/FlowBuilderCoreProvider.tsx
  • frontend/apps/console/src/features/flows/context/StepPreviewContext.tsx
  • frontend/apps/console/src/features/flows/context/__tests__/FlowBuilderCoreProvider.test.tsx
  • frontend/apps/console/src/features/flows/hooks/useFlowSimulation.ts
  • frontend/apps/console/src/features/flows/hooks/useRenameStep.ts
  • frontend/apps/console/src/features/flows/hooks/useResourceFieldError.ts
  • frontend/apps/console/src/features/flows/hooks/useStepPreview.ts
  • frontend/apps/console/src/features/flows/models/base.ts
  • frontend/apps/console/src/features/flows/models/steps.ts
  • frontend/apps/console/src/features/flows/utils/__tests__/reactFlowTransformer.test.ts
  • frontend/apps/console/src/features/flows/utils/__tests__/resolveStepMetadata.test.ts
  • frontend/apps/console/src/features/flows/utils/__tests__/updateTemplatePlaceholderReferences.test.ts
  • frontend/apps/console/src/features/flows/utils/reactFlowTransformer.ts
  • frontend/apps/console/src/features/flows/utils/updateTemplatePlaceholderReferences.ts
  • frontend/apps/console/src/features/login-flow/components/LoginFlowBuilder.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/CallProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/FieldExtendedProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/__tests__/ExecutionExtendedProperties.test.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/CheckboxWithHint.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/EmailProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/ExecutorInputsEditor.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/FederationProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/HttpRequestProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OUExecutorProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OUResolverProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OpenID4VPProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OtpProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/PermissionValidatorProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/ProvisioningProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/SmsProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/UserTypeResolverProperties.tsx
  • frontend/apps/console/src/features/login-flow/data/executors.json
  • frontend/apps/console/src/features/login-flow/data/templates.json
  • frontend/apps/console/src/features/login-flow/data/widgets.json
  • frontend/apps/console/src/layouts/DashboardLayout.tsx
  • frontend/packages/i18n/src/locales/en-US.ts
💤 Files with no reviewable changes (4)
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/tests/GithubExecution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GithubExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/GoogleExecution.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/tests/GoogleExecution.test.tsx
🚧 Files skipped from review as they are similar to previous changes (64)
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/SmsProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OUResolverProperties.tsx
  • frontend/apps/console/src/features/flows/models/base.ts
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/PermissionValidatorProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/UserTypeResolverProperties.tsx
  • frontend/apps/console/src/features/flows/context/StepPreviewContext.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.scss
  • frontend/apps/console/src/features/flows/components/react-flow-overrides/tests/BaseEdge.test.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OtpProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/EmailProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OUExecutorProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/ProvisioningProperties.tsx
  • frontend/apps/console/src/features/flows/hooks/useResourceFieldError.ts
  • frontend/apps/console/src/features/login-flow/components/LoginFlowBuilder.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/PanelActionButton.tsx
  • frontend/apps/console/src/features/flows/context/tests/FlowBuilderCoreProvider.test.tsx
  • frontend/apps/console/src/features/flows/hooks/useRenameStep.ts
  • frontend/apps/console/src/features/flows/components/visual-flow/tests/SimulationStepPreview.test.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/HttpRequestProperties.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/tests/ExecutionMinimal.test.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/CheckboxWithHint.tsx
  • frontend/apps/console/src/App.tsx
  • frontend/apps/console/src/features/login-flow/data/widgets.json
  • frontend/apps/console/src/features/flows/components/resources/steps/view/ReorderableElement.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/VariantSelect.tsx
  • frontend/apps/console/src/features/flows/components/react-flow-overrides/BaseEdge.tsx
  • frontend/apps/console/src/features/flows/utils/tests/reactFlowTransformer.test.ts
  • frontend/apps/console/src/features/flows/components/resources/steps/call/Call.tsx
  • frontend/apps/console/src/features/flows/utils/updateTemplatePlaceholderReferences.ts
  • frontend/apps/console/src/features/flows/components/visual-flow/DecoratedVisualFlow.tsx
  • frontend/apps/console/src/features/flows/hooks/useStepPreview.ts
  • frontend/apps/console/src/features/login-flow/data/executors.json
  • frontend/packages/i18n/src/locales/en-US.ts
  • frontend/apps/console/src/features/flows/hooks/useFlowSimulation.ts
  • frontend/apps/console/src/features/flows/components/ResourceDisplayImage.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/Execution.tsx
  • frontend/apps/console/src/features/flows/context/FlowBuilderCoreProvider.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/CheckboxPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/rich-text/RichTextWithTranslation.tsx
  • frontend/apps/console/src/features/flows/components/visual-flow/tests/DecoratedVisualFlow.test.tsx
  • frontend/apps/console/src/features/flows/components/resource-panel/ResourcePanelItem.tsx
  • frontend/apps/console/src/features/flows/components/resources/elements/adapters/ButtonAdapter.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/tests/ResourcePropertyPanel.test.tsx
  • frontend/apps/console/src/features/flows/utils/tests/updateTemplatePlaceholderReferences.test.ts
  • frontend/apps/console/src/features/flows/components/validation-panel/tests/ValidationPanel.test.tsx
  • frontend/apps/console/src/features/flows/components/validation-panel/ValidationPanel.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/OpenID4VPProperties.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/call/tests/Call.test.tsx
  • frontend/apps/console/src/features/flows/utils/reactFlowTransformer.ts
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/CallProperties.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ResourceProperties.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/tests/View.test.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/FieldExtendedProperties.tsx
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/tests/ExecutionExtendedProperties.test.tsx
  • frontend/apps/console/src/features/flows/utils/tests/resolveStepMetadata.test.ts
  • frontend/apps/console/src/features/login-flow/components/resource-property-panel/extended-properties/execution-properties/FederationProperties.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/ResourcePropertyPanel.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/tests/StepTitle.test.tsx
  • frontend/apps/console/src/features/flows/components/resource-property-panel/TextPropertyField.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/execution-factory/tests/ExecutionFactory.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/tests/Execution.test.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/execution/ExecutionMinimal.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/view/View.tsx
  • frontend/apps/console/src/features/flows/components/resources/steps/StepTitle.tsx

@DonOmalVindula
DonOmalVindula enabled auto-merge July 20, 2026 06:45
@DonOmalVindula
DonOmalVindula added this pull request to the merge queue Jul 20, 2026
Merged via the queue into thunder-id:main with commit d9d6458 Jul 20, 2026
24 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants