perf(web): refine channel test dialog interactions - #5886
Conversation
- split model test status from result details so failures and latency no longer crowd one column. - move batch progress into toast updates to keep the dialog height stable during tests. - consolidate the channel title and model actions to reduce vertical churn.
- replace per-model test text buttons with icon-only actions matching the channel list. - let the action column shrink to its icon content to reduce table width.
WalkthroughRefactors the channel batch-test dialog UI and behavior: import formatting, error normalization using replaceAll, a persistent toast.loading for batch progress replacing the progress bar, adjusted column sizing, restructured status/result cell rendering, redesigned per-row action button, and reorganized header/footer/toolbar layout. ChangesChannel test dialog refactor
Estimated code review effort: 3 (Moderate) | ~25 minutes Possibly related PRs
Suggested reviewers: Poem
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
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. Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 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
`@web/default/src/features/channels/components/dialogs/channel-test-dialog.tsx`:
- Around line 367-399: The batch progress toast in channel-test-dialog should
stay visible for the full batch run instead of inheriting the default
auto-dismiss timeout. Update the toast.loading call inside the batch progress
useEffect so it explicitly uses an infinite duration, while keeping the existing
dismissBatchProgressToast cleanup and toast id reuse logic intact. Use the
batchProgressToastIdRef, dismissBatchProgressToast, and toast.loading references
to locate the change.
🪄 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: Organization UI
Review profile: CHILL
Plan: Pro
Run ID: c1f2aeb3-da17-41f8-9fea-249d48c7c1a5
📒 Files selected for processing (1)
web/default/src/features/channels/components/dialogs/channel-test-dialog.tsx
| const dismissBatchProgressToast = useCallback(() => { | ||
| if (batchProgressToastIdRef.current === null) return | ||
|
|
||
| toast.dismiss(batchProgressToastIdRef.current) | ||
| batchProgressToastIdRef.current = null | ||
| }, []) | ||
|
|
||
| useEffect(() => { | ||
| if (!batchProgress) { | ||
| dismissBatchProgressToast() | ||
| return | ||
| } | ||
|
|
||
| const title = isBatchStopRequested | ||
| ? t('Stopping batch test...') | ||
| : t('Batch testing models...') | ||
| const completedText = t('{{completed}}/{{total}} completed', { | ||
| completed: batchProgress.completed, | ||
| total: batchProgress.total, | ||
| }) | ||
| const resultText = t('{{success}} succeeded, {{failed}} failed', { | ||
| success: batchProgress.success, | ||
| failed: batchProgress.failed, | ||
| }) | ||
|
|
||
| batchProgressToastIdRef.current = toast.loading(title, { | ||
| id: batchProgressToastIdRef.current ?? undefined, | ||
| description: `${completedText} · ${resultText}`, | ||
| }) | ||
| }, [batchProgress, dismissBatchProgressToast, isBatchStopRequested, t]) | ||
|
|
||
| useEffect(() => dismissBatchProgressToast, [dismissBatchProgressToast]) | ||
|
|
There was a problem hiding this comment.
🩺 Stability & Availability | 🟡 Minor | ⚡ Quick win
🧩 Analysis chain
🌐 Web query:
sonner toast.loading default duration Infinity vs Toaster duration prop
💡 Result:
In Sonner, the duration prop on the <Toaster /> component sets the default global duration for all toasts, while setting duration: Infinity on an individual toast() call (including toast.loading) is the recommended way to keep a specific toast visible indefinitely until it is manually dismissed or updated [1][2][3]. Key distinctions and technical details: 1. Global vs. Local Duration: The <Toaster /> duration prop (default 4000ms) establishes the automatic dismissal time for all toasts that do not have an explicit duration set [4][5][3]. Individual toast calls override this global setting [3]. 2. Using Infinity: Setting duration: Infinity on a toast (e.g., toast.loading('Loading...', { duration: Infinity })) effectively disables the automatic close timer [6][1][2]. Internally, Sonner includes logic to check for this value to avoid calling setTimeout with Infinity, which would otherwise cause the toast to close immediately [6][7]. 3. Common Patterns: For loading states, it is common practice to set duration: Infinity so the toast remains on screen until the associated asynchronous operation completes. Once finished, you can update the toast by referencing its ID (returned by toast.loading) and calling toast.success or toast.error with a standard duration to allow the final message to dismiss automatically [1][8]. Note: If you encounter issues where duration: Infinity causes a toast not to render, ensure you are using a compatible version of the library, as earlier versions had reported bugs regarding infinite timers [7][9].
Citations:
- 1: Provide more control on how I control the toast states! emilkowalski/sonner#163
- 2: Toast remain open indefinitely until the user closes it emilkowalski/sonner#327
- 3: toast.promise duration emilkowalski/sonner#89
- 4: https://emilkowal.ski/ui/building-a-toast-component
- 5: https://www.shadcn.io/examples/sonner-toast-with-custom-duration
- 6: https://github.com/emilkowalski/sonner/blob/main/src/index.tsx
- 7: fix: toast not displaying when
Toaster.durationis set to Infinity emilkowalski/sonner#373 - 8: Inability to update toast
durationdynamically emilkowalski/sonner#529 - 9: duration: Infinity silently breaks toasts emilkowalski/sonner#287
🏁 Script executed:
#!/bin/bash
set -euo pipefail
printf '\n== Toaster config ==\n'
ast-grep outline web/default/src/routes/__root.tsx --view expanded || true
printf '\n-- relevant lines --\n'
sed -n '1,140p' web/default/src/routes/__root.tsx | cat -n
printf '\n== batch progress toast callsite ==\n'
sed -n '340,430p' web/default/src/features/channels/components/dialogs/channel-test-dialog.tsx | cat -n
printf '\n== sonner dependency version ==\n'
if [ -f package.json ]; then
rg -n '"sonner"|sonner@' package.json bun.lock* pnpm-lock.yaml package-lock.json yarn.lock -S || true
fiRepository: QuantumNous/new-api
Length of output: 9199
🏁 Script executed:
#!/bin/bash
set -euo pipefail
printf '\n== Sonner wrapper ==\n'
fd -a 'sonner.tsx' web/default/src/components web/default/src -t f || true
fd -a 'sonner.ts' web/default/src/components web/default/src -t f || true
for f in $(fd -a 'sonner.*' web/default/src -t f); do
echo "--- $f ---"
sed -n '1,200p' "$f" | cat -n
done
printf '\n== batch test cadence / delay constants ==\n'
rg -n 'BATCH_TEST_DELAY_MS|batchProgress|setBatchProgress|toast\.loading|toast\.dismiss|isBatchStopRequested' web/default/src/features/channels -S
printf '\n== surrounding batch test logic ==\n'
sed -n '220,420p' web/default/src/features/channels/components/dialogs/channel-test-dialog.tsx | cat -nRepository: QuantumNous/new-api
Length of output: 14943
🌐 Web query:
Sonner toast.loading default duration loading toasts inherit Toaster duration or Infinity
💡 Result:
In Sonner, a toast.loading call does not automatically default to Infinity [1][2]. It inherits the default duration set on the <Toaster /> component (which is 4000ms by default) [3][4][1]. If you want a toast.loading toast to stay visible indefinitely until you manually update or dismiss it, you must explicitly set the duration to Infinity [1][2]: javascript toast.loading("Loading...", { duration: Infinity }); This behavior is by design [1]. Because toast.loading follows the standard toast lifecycle, it will automatically close after the set duration unless duration: Infinity is provided or the toast is updated (e.g., replaced by a toast.success or toast.error using the same ID) [1][2].
Citations:
- 1: It is not clear in docs how to control the toast states on-demand instead of auto behavior! emilkowalski/sonner#173
- 2: Provide more control on how I control the toast states! emilkowalski/sonner#163
- 3: https://emilkowal.ski/ui/building-a-toast-component
- 4: http://codesandbox.io/p/github/willnguyen1312/sonner
Keep the batch progress toast visible until the batch finishes web/default/src/features/channels/components/dialogs/channel-test-dialog.tsx:392
toast.loading inherits the global duration={5000} here, so this progress toast can disappear mid-run between updates. Pass duration: Infinity to keep it on screen until it’s dismissed or replaced.
🤖 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 `@web/default/src/features/channels/components/dialogs/channel-test-dialog.tsx`
around lines 367 - 399, The batch progress toast in channel-test-dialog should
stay visible for the full batch run instead of inheriting the default
auto-dismiss timeout. Update the toast.loading call inside the batch progress
useEffect so it explicitly uses an infinite duration, while keeping the existing
dismissBatchProgressToast cleanup and toast id reuse logic intact. Use the
batchProgressToastIdRef, dismissBatchProgressToast, and toast.loading references
to locate the change.
Merge pull request QuantumNous#5886 from QuantumNous/perf/channel-test-dialog-layout
Merge pull request QuantumNous#5886 from QuantumNous/perf/channel-test-dialog-layout
Merge pull request QuantumNous#5886 from QuantumNous/perf/channel-test-dialog-layout
Important
📝 变更描述 / Description
优化渠道测试弹窗的模型测试结果展示与操作布局。模型测试状态和测试结果拆分为独立列,失败摘要、详情入口和响应耗时不再挤在状态列中;批量测试进度改为 toast 更新,避免测试开始和结束时改变弹窗高度;标题、顶部操作区和行内测试按钮也做了压缩整理,让整体布局更稳定。
🚀 变更类型 / Type of change
🔗 关联任务 / Related Issue
✅ 提交前检查项 / Checklist
Bug fix,我已提交或关联对应 Issue,且不会将设计取舍、预期不一致或理解偏差直接归类为 bug。📸 运行证明 / Proof of Work
bunx oxfmt --check src/features/channels/components/dialogs/channel-test-dialog.tsxbunx oxlint -c .oxlintrc.json src/features/channels/components/dialogs/channel-test-dialog.tsxgit diff --checkbefore

after

Summary by CodeRabbit
UI Improvements
Bug Fixes