Skip to content

fix(ui): close first-contact UX gaps across the web interface - #2531

Merged
yohamta0 merged 12 commits into
mainfrom
ui-ux-cheap-wins
Aug 8, 2026
Merged

yohamta0 merged 12 commits into
mainfrom
ui-ux-cheap-wins

Conversation

@yohamta0

@yohamta0 yohamta0 commented Aug 8, 2026 •

Copy link
Copy Markdown
Member

Summary

Eleven small, self-contained fixes from a UX audit of the web UI, each targeting a moment that shapes a newcomer's first impression:

  • Running graph nodes now pulse (the `animate` prop was dead code); dead `showIcons`/`animate` props removed
  • The DAG editor no longer auto-formats on mount and on every newline, which marked untouched files as modified (23% of doc-style YAML was rewritten on open) and armed the external-change conflict dialog
  • Backend validation errors render monospace with line breaks preserved instead of collapsing into a muted 450px paragraph; empty error arrays no longer count as failures
  • Per-step retry is labeled honestly ("Retry this step"; the API retries only that step) and confirms success with a toast and refresh
  • The primary DAG action is labeled "Start", matching its tooltip, the modal, and `dagu start`
  • The executions list no longer flashes "No DAG runs found" while the first page loads
  • Empty states stop blaming filters the user never set; a pristine install now invites creating the first workflow
  • The DAG JSON schema carries `examples` for high-traffic properties, lighting up the docs sidebar Examples panel, hover cards, and completion snippets at once
  • The browser tab title reflects the current page instead of the static "Dagu"
  • Copy-YAML button on the spec editor (read-only viewers included) and Copy-link button on the run header; the three hand-rolled copy-feedback blocks consolidate into `useCopyFeedback`
  • Rejected v1 `executor:` keys now hint the `action`/`with` replacement, and renamed keys (`precondition`, `dir`) get accurate hints instead of being mislabeled as snake_case fixes

Validation

  • `cd ui && pnpm test` (624 tests), `pnpm exec tsc --noEmit`, `pnpm build`
  • `go test ./internal/core/spec/...`, `golangci-lint run internal/core/spec/...`
  • `ui/e2e/helpers/e2e.ts` updated for the Start rename (exercised by `distributed-stack.spec.ts` in CI)

Summary by cubic

Improves first‑time UX across the web UI with small, focused changes. Adds clearer actions, better errors, helpful examples, and easier sharing.

  • New Features

    • Running nodes pulse in graphs; removed dead showIcons/animate props.
    • Copy buttons: YAML in the spec editor and run link in run headers, with unified useCopyFeedback.
    • Browser tab title reflects the current page title.
    • DAG JSON schema now includes examples for common fields to power docs, hover cards, and editor completion.
  • Bug Fixes

    • Editor and errors: no auto‑format on open or Enter; empty validation error arrays don’t block saves; error modal renders details in monospace with preserved line breaks.
    • Action clarity: primary DAG action is “Start”; per‑step retry is “Retry this step” and shows a success toast and refreshes.
    • Lists and empty states: executions no longer flash “No DAG runs” during initial load (shows a loading row); workflow empty states no longer blame filters and invite creating the first workflow; runs copy is date‑range aware.
    • Spec hints: legacy key guidance now suggests replacements (e.g., executor -> action + with, precondition -> preconditions, dir -> working_dir).
    • Graphs: include graph type in memo deps to prevent stale definitions when switching modes.

Written for commit e9525df. Summary will update on new commits.

Review in cubic

Summary by CodeRabbit

  • New Features

    • Added copy actions for DAG names, YAML specifications, documentation, and DAG run links with visual confirmation.
    • Added clearer workflow and DAG-run empty states, including loading indicators and relevant actions.
    • Added running-node pulse animations that respect reduced-motion preferences.
    • Improved error dialogs with structured validation details and readable formatting.
    • Browser titles now reflect the current page and configured application name.
  • Improvements

    • Renamed the primary workflow action from “Enqueue” to “Start.”
    • Retry actions now show success notifications and refresh workflow details.
    • Configuration validation errors provide clearer guidance for renamed or removed settings.

yohamta0 added 11 commits August 8, 2026 13:14
The mount-time formatDocument rewrote files the user never touched, lighting up Save/Discard and arming the external-change conflict dialog on first open. formatOnType reformatted the whole document on every Enter. Manual format (Shift+Alt+F) still works.
Backend validation errors (line:column prefixes and caret excerpts) were passed as the modal's hint, which collapses newlines into one muted proportional-font paragraph. Add a details channel rendered monospace with line breaks preserved, and stop treating an empty errors array as a failure on spec save.
The retry action re-executes only the selected step, but the tooltip and dialog title said "Retry from this step". Rename to match the API contract, and give the success path the same toast plus refresh the run-level retry already has instead of silently closing the dialog.
The header button said Enqueue while its tooltip, the modal it opens, and the CLI all say start. The modal still switches to Enqueue wording when the queue toggle is on.
The executions list rendered "No DAG runs found" while the first page was still loading, then swapped in the table. Thread the pagination hook's initial-loading flag into both list views and show a quiet inline loading row instead.
The workflow list told users with zero workflows to adjust filters they never set. Branch the copy: a pristine all-workflows view now invites creating the first workflow. The runs empty state is reworded to be range-aware instead of presuming filters, and the duplicated workflow empty-state markup is extracted into one component.
The schema doc sidebar has an Examples panel, and monaco-yaml surfaces schema examples in hover, value completion, and property snippets, but the schema carried none. Seed concise examples for the most-used DAG and step properties.
Every tab, bookmark, and history entry read the static "Dagu". Pages already publish their titles through AppBarContext; mirror that into document.title.
Sharing a workflow required select-all inside Monaco, and sharing a run meant grabbing the address bar. Add a Copy button to the spec editor header (visible to read-only viewers too) and a Copy link button on the run header. The three hand-rolled copy-feedback blocks consolidate into a useCopyFeedback hook.
…used

The v1 executor key was rejected with a bare invalid-keys error while 70+ other legacy keys get migration hints, and renamed keys (precondition, dir) were mislabeled as snake_case fixes. Split the hint map into casing renames and removed keys with full replacement clauses, and drop the dead run->call entry (run is a valid v2 step key).
@coderabbitai

coderabbitai Bot commented Aug 8, 2026 •

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

The PR adds schema examples and legacy-key migration hints. It extends structured validation-error display, centralizes copy feedback, adds DAG run loading states, and updates workflow, graph, editor, title, and retry UI behavior with tests.

Changes

DAG schema and diagnostics

Layer / File(s) Summary
Schema examples and legacy-key diagnostics
internal/cmn/schema/dag.schema.json, internal/core/spec/*
Schema properties now include example values. Decoder errors now include rename and removed-key migration hints.
Structured validation error display
ui/src/components/ui/error-modal.tsx, ui/src/features/dags/components/dag-editor/*, ui/src/pages/base-config/index.tsx
Error modals render structured diagnostic details. Validation callers pass error collections instead of joined strings.

UI behavior

Layer / File(s) Summary
Shared copy feedback and copy actions
ui/src/hooks/*, ui/src/features/dags/components/dag-details/DAGHeader.tsx, ui/src/features/dags/components/dag-editor/DAGSpec.tsx, ui/src/pages/docs/components/DocEditor.tsx
A shared hook manages clipboard feedback. DAG, YAML, document, and run-link actions use the hook.
DAG run loading states
ui/src/pages/dag-runs/*, ui/src/features/dag-runs/components/dag-run-list/*
Initial loading state flows from pagination to table and grouped views. Empty results now show loading or empty-state text as appropriate.
Workflow empty states and retry feedback
ui/src/features/dags/components/dag-list/*, ui/src/features/dags/components/dag-details/*, ui/src/features/dags/components/common/DAGActions.tsx, ui/e2e/helpers/e2e.ts
Workflow empty states vary by filters. Successful retries show a toast and refresh context. The primary action is labeled “Start”.
Graph, editor, and motion behavior
ui/src/features/dags/components/visualization/*, ui/src/features/dags/components/DAGStatus.tsx, ui/src/features/dags/components/dag-editor/DAGEditor.tsx, ui/src/styles/global.css
Graph icon and animation props were removed. Editor auto-formatting was disabled. Running Mermaid nodes pulse when reduced motion is not requested.
Browser document titles
ui/src/App.tsx, ui/src/__tests__/App.test.tsx
The browser title combines the page title with the configured application title and falls back to Dagu or the configured title.

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

Possibly related PRs

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 39.13% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
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.
Title check ✅ Passed The title clearly summarizes the PR's main change: addressing first-contact UX issues across the web interface.
Description check ✅ Passed The description provides a detailed summary of changes and validation steps, but it omits the template's explicit Changes, Related Issues, and Checklist sections.
✨ Finishing Touches 💡 1
📝 Generate docstrings 💡
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch ui-ux-cheap-wins

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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 2

🧹 Nitpick comments (5)
ui/src/hooks/__tests__/useCopyFeedback.test.tsx (1)

20-45: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Test timer replacement after repeated copies.

Call copy() a second time before the first reset expires. Assert that copied remains true until resetMs after the second call. This verifies the timer replacement at useCopyFeedback.ts Line 23.

As per coding guidelines, TypeScript changes require appropriate tests.

Proposed test
+  it('restarts feedback after a later successful copy', async () => {
+    vi.useFakeTimers();
+    copyTextMock.mockResolvedValue(true);
+    const { result } = renderHook(() => useCopyFeedback());
+
+    await act(async () => {
+      await result.current.copy('first');
+    });
+    act(() => vi.advanceTimersByTime(1000));
+    await act(async () => {
+      await result.current.copy('second');
+    });
+
+    act(() => vi.advanceTimersByTime(1000));
+    expect(result.current.copied).toBe(true);
+    act(() => vi.advanceTimersByTime(1000));
+    expect(result.current.copied).toBe(false);
+  });
🤖 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 `@ui/src/hooks/__tests__/useCopyFeedback.test.tsx` around lines 20 - 45, Add a
test alongside the existing useCopyFeedback cases that performs two successful
copy calls before the first reset expires, advances fake timers to confirm
copied remains true, then advances through resetMs measured from the second call
and confirms it becomes false. Reuse the existing copyTextMock, renderHook, and
timer setup to verify the reset timer replacement in useCopyFeedback.

Source: Coding guidelines

ui/src/features/dag-runs/components/dag-run-details/DAGRunHeader.tsx (1)

44-54: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add coverage for both generated run-link modes.

The existing test covers root and sub-run URL shapes, but this copy-link path is also in DAGRunHeader.tsx and uses non-root config.basePath. Add coverage for both run types with a non-root base path if it is not already present.

🤖 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 `@ui/src/features/dag-runs/components/dag-run-details/DAGRunHeader.tsx` around
lines 44 - 54, Add tests for the DAGRunHeader copyRunLink flow covering both
root and sub-run links when config.basePath is a non-root value. Verify the
copied URLs include the configured base path and the correct run-path shape,
reusing the existing root/sub-run URL test setup where possible.

Source: Coding guidelines

ui/src/pages/dag-runs/__tests__/index.test.tsx (1)

198-213: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Cover the grouped-view loading prop.

This test captures DAGRunTable props only. It does not verify that DAGRuns passes isLoading to DAGRunGroupedView at ui/src/pages/dag-runs/index.tsx Line 1061. Add grouped-view prop capture or run the assertion for both view modes.

As per coding guidelines, ui/**/*.{ts,tsx} changes must add or update appropriate tests; this test does not exercise the grouped-view wiring.

🤖 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 `@ui/src/pages/dag-runs/__tests__/index.test.tsx` around lines 198 - 213,
Extend the initial-loading test around renderPage and the view-mode setup to
exercise the grouped view as well as the table view. Capture DAGRunGroupedView
props, render with grouped view selected, and assert its isLoading prop is true,
while preserving the existing DAGRunTable assertion.

Source: Coding guidelines

ui/src/features/dags/components/dag-list/DAGTable.tsx (1)

1004-1005: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Use the prescribed text color hierarchy.

WorkflowsEmptyState uses text-foreground for primary text and text-muted-foreground for muted text. Use the specified slate classes for this new UI.

As per coding guidelines, use text-slate-800 dark:text-slate-200 for primary text and text-slate-500 dark:text-slate-500 for muted text.

Proposed class update
-      <h3 className="text-lg font-medium text-foreground mb-2">{heading}</h3>
+      <h3 className="text-lg font-medium text-slate-800 dark:text-slate-200 mb-2">
+        {heading}
+      </h3>
-      <p className="text-sm text-muted-foreground text-center max-w-md mb-4 whitespace-normal break-words">
+      <p className="text-sm text-slate-500 dark:text-slate-500 text-center max-w-md mb-4 whitespace-normal break-words">
🤖 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 `@ui/src/features/dags/components/dag-list/DAGTable.tsx` around lines 1004 -
1005, Update the heading and descriptive paragraph in the empty-state UI to use
the prescribed slate color hierarchy: apply text-slate-800 dark:text-slate-200
to the primary heading and text-slate-500 dark:text-slate-500 to the muted
paragraph, replacing the existing text-foreground and text-muted-foreground
classes.

Source: Coding guidelines

ui/src/features/dags/components/dag-list/__tests__/DAGTable.test.tsx (1)

422-430: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Cover the remaining empty-state branches.

This test covers only the pristine all-workflows branch. Add cases for filtered results and a named workflow view. Assert the generic message and the Show all workflows action where applicable.

As per coding guidelines, TypeScript changes should include tests appropriate to the changed code.

🤖 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 `@ui/src/features/dags/components/dag-list/__tests__/DAGTable.test.tsx` around
lines 422 - 430, Expand the DAGTable empty-state tests around the existing “no
workflows yet” case to cover an empty filtered result and an empty
named-workflow view. Assert the generic “No workflows found” message and the
“Show all workflows” action for the filtered branch where applicable, while
preserving the existing pristine-state assertions.

Source: Coding guidelines

🤖 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 `@ui/src/__tests__/App.test.tsx`:
- Around line 217-221: Update the “falls back to the configured title when a
page sets none” test to provide a non-default custom config.title before
rendering /queues, then assert document.title equals that custom value while
preserving the existing heading assertion. Ensure the test exercises
configured-title propagation rather than only the default “Dagu” fallback.

In `@ui/src/features/dags/components/visualization/Graph.tsx`:
- Line 393: Update the graph memoization dependency list in Graph so it includes
the type value used by the type === 'status' branch, ensuring the graph
recomputes when type changes while preserving the existing dependencies.

---

Nitpick comments:
In `@ui/src/features/dag-runs/components/dag-run-details/DAGRunHeader.tsx`:
- Around line 44-54: Add tests for the DAGRunHeader copyRunLink flow covering
both root and sub-run links when config.basePath is a non-root value. Verify the
copied URLs include the configured base path and the correct run-path shape,
reusing the existing root/sub-run URL test setup where possible.

In `@ui/src/features/dags/components/dag-list/__tests__/DAGTable.test.tsx`:
- Around line 422-430: Expand the DAGTable empty-state tests around the existing
“no workflows yet” case to cover an empty filtered result and an empty
named-workflow view. Assert the generic “No workflows found” message and the
“Show all workflows” action for the filtered branch where applicable, while
preserving the existing pristine-state assertions.

In `@ui/src/features/dags/components/dag-list/DAGTable.tsx`:
- Around line 1004-1005: Update the heading and descriptive paragraph in the
empty-state UI to use the prescribed slate color hierarchy: apply text-slate-800
dark:text-slate-200 to the primary heading and text-slate-500
dark:text-slate-500 to the muted paragraph, replacing the existing
text-foreground and text-muted-foreground classes.

In `@ui/src/hooks/__tests__/useCopyFeedback.test.tsx`:
- Around line 20-45: Add a test alongside the existing useCopyFeedback cases
that performs two successful copy calls before the first reset expires, advances
fake timers to confirm copied remains true, then advances through resetMs
measured from the second call and confirms it becomes false. Reuse the existing
copyTextMock, renderHook, and timer setup to verify the reset timer replacement
in useCopyFeedback.

In `@ui/src/pages/dag-runs/__tests__/index.test.tsx`:
- Around line 198-213: Extend the initial-loading test around renderPage and the
view-mode setup to exercise the grouped view as well as the table view. Capture
DAGRunGroupedView props, render with grouped view selected, and assert its
isLoading prop is true, while preserving the existing DAGRunTable assertion.
🪄 Autofix

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: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 5d2acfbf-1429-4a35-bae6-df895f6790af

📥 Commits

Reviewing files that changed from the base of the PR and between 3098d31 and 927d16b.

📒 Files selected for processing (37)
  • internal/cmn/schema/dag.schema.json
  • internal/core/spec/builder.go
  • internal/core/spec/dag.go
  • internal/core/spec/defaults.go
  • internal/core/spec/key_hints.go
  • internal/core/spec/loader_test.go
  • internal/core/spec/manifest_decoder.go
  • ui/e2e/helpers/e2e.ts
  • ui/src/App.tsx
  • ui/src/__tests__/App.test.tsx
  • ui/src/components/ui/__tests__/error-modal.test.tsx
  • ui/src/components/ui/error-modal.tsx
  • ui/src/features/dag-runs/components/dag-run-details/DAGRunHeader.tsx
  • ui/src/features/dag-runs/components/dag-run-list/DAGRunGroupedView.tsx
  • ui/src/features/dag-runs/components/dag-run-list/DAGRunTable.tsx
  • ui/src/features/dag-runs/components/dag-run-list/__tests__/DAGRunGroupedView.test.tsx
  • ui/src/features/dag-runs/components/dag-run-list/__tests__/DAGRunTable.test.tsx
  • ui/src/features/dags/components/DAGStatus.tsx
  • ui/src/features/dags/components/common/DAGActions.tsx
  • ui/src/features/dags/components/dag-details/DAGHeader.tsx
  • ui/src/features/dags/components/dag-details/NodeStatusTableRow.tsx
  • ui/src/features/dags/components/dag-details/__tests__/NodeStatusTableRow.test.tsx
  • ui/src/features/dags/components/dag-editor/DAGEditor.tsx
  • ui/src/features/dags/components/dag-editor/DAGSpec.tsx
  • ui/src/features/dags/components/dag-editor/DAGSpecReadOnly.tsx
  • ui/src/features/dags/components/dag-list/DAGTable.tsx
  • ui/src/features/dags/components/dag-list/__tests__/DAGTable.test.tsx
  • ui/src/features/dags/components/visualization/DAGGraph.tsx
  • ui/src/features/dags/components/visualization/Graph.tsx
  • ui/src/features/dags/components/visualization/__tests__/Graph.test.tsx
  • ui/src/hooks/__tests__/useCopyFeedback.test.tsx
  • ui/src/hooks/useCopyFeedback.ts
  • ui/src/pages/base-config/index.tsx
  • ui/src/pages/dag-runs/__tests__/index.test.tsx
  • ui/src/pages/dag-runs/index.tsx
  • ui/src/pages/docs/components/DocEditor.tsx
  • ui/src/styles/global.css
💤 Files with no reviewable changes (2)
  • ui/src/features/dags/components/DAGStatus.tsx
  • ui/src/features/dags/components/visualization/tests/Graph.test.tsx

Comment thread ui/src/__tests__/App.test.tsx Outdated
Comment on lines +217 to +221
it('falls back to the configured title when a page sets none', async () => {
renderAt('/queues');

expect(await screen.findByRole('heading', { name: 'Queues' })).toBeVisible();
expect(document.title).toBe('Dagu');

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Test a non-default configured title.

Lines 217-221 only verify the default value, Dagu. Pass a custom config.title and expect that value. The test must detect a regression that ignores the configured application title.

Proposed test update
   it('falls back to the configured title when a page sets none', async () => {
-    renderAt('/queues');
+    renderAt('/queues', makeConfig({ title: 'Operations' }));

     expect(await screen.findByRole('heading', { name: 'Queues' })).toBeVisible();
-    expect(document.title).toBe('Dagu');
+    expect(document.title).toBe('Operations');
   });
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
it('falls back to the configured title when a page sets none', async () => {
renderAt('/queues');
expect(await screen.findByRole('heading', { name: 'Queues' })).toBeVisible();
expect(document.title).toBe('Dagu');
it('falls back to the configured title when a page sets none', async () => {
renderAt('/queues', makeConfig({ title: 'Operations' }));
expect(await screen.findByRole('heading', { name: 'Queues' })).toBeVisible();
expect(document.title).toBe('Operations');
🤖 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 `@ui/src/__tests__/App.test.tsx` around lines 217 - 221, Update the “falls back
to the configured title when a page sets none” test to provide a non-default
custom config.title before rendering /queues, then assert document.title equals
that custom value while preserving the existing heading assertion. Ensure the
test exercises configured-title propagation rather than only the default “Dagu”
fallback.


return dat.join('\n');
}, [steps, onClickNode, flowchart, showIcons, isDarkMode]);
}, [steps, onClickNode, flowchart, isDarkMode]);

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

rg -n -C 10 \
  'const graph = React\.useMemo|type === .status.|^\s*\}, \[steps,.*flowchart' \
  ui/src/features/dags/components/visualization/Graph.tsx

Repository: dagucloud/dagu

Length of output: 2957


Add type to the graph memo dependencies.

graph branches on type === 'status', but the dependency list omits type. When type changes without steps, graph can still use the previous graph definition.

Proposed fix
-  }, [steps, onClickNode, flowchart, isDarkMode]);
+  }, [steps, type, onClickNode, flowchart, isDarkMode]);
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
}, [steps, onClickNode, flowchart, isDarkMode]);
}, [steps, type, onClickNode, flowchart, isDarkMode]);
🤖 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 `@ui/src/features/dags/components/visualization/Graph.tsx` at line 393, Update
the graph memoization dependency list in Graph so it includes the type value
used by the type === 'status' branch, ensuring the graph recomputes when type
changes while preserving the existing dependencies.

The graph definition memo branches on the graph type but omitted it from its dependency list, and the fallback-title test only exercised the default value.
@yohamta0
yohamta0 merged commit 9ef2125 into main Aug 8, 2026
20 of 21 checks passed
@yohamta0
yohamta0 deleted the ui-ux-cheap-wins branch August 8, 2026 06:52
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