-
Notifications
You must be signed in to change notification settings - Fork 4k
[feat] Replace inline error messages with tooltips in st.chat_input file upload UI
#13542
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
✅ Snyk checks have passed. No issues have been found so far.
💻 Catch issues earlier using the plugins for VS Code, JetBrains IDEs, Visual Studio, and Eclipse. |
✅ PR preview is ready!
|
This stack of pull requests is managed by Graphite. Learn more about stacking. |
📈 Frontend coverage change detectedThe frontend unit test (vitest) coverage has increased by 0.0200%
✅ Coverage change is within normal range. |
ed68149 to
dbd224c
Compare
5c4ff72 to
7992f54
Compare
56c60d9 to
8b7b2fb
Compare
114c830 to
cc7e6e4
Compare
8b7b2fb to
ca26e50
Compare
ca26e50 to
c403751
Compare
cc7e6e4 to
44c5a57
Compare
st.chat_input file upload UI
44c5a57 to
111ca6a
Compare
c403751 to
ab30b4c
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull request overview
This PR replaces inline error messages with hover tooltips in the st.chat_input file upload UI to create a more compact and visually clean design. Error messages are now displayed in tooltips when users hover over file chips in an error state, using the standard Tooltip component.
Key Changes
- Removed inline error display in favor of tooltip-based error messages
- File chips now show file size consistently, with errors appearing only on hover
- Updated E2E tests to verify tooltip behavior and interactions
Reviewed changes
Copilot reviewed 3 out of 15 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
frontend/lib/src/components/widgets/ChatInput/fileUpload/ChatUploadedFile.tsx |
Refactored to conditionally wrap error file chips in Tooltip component; removed inline error text display |
frontend/lib/src/components/widgets/ChatInput/fileUpload/styled-components.ts |
Removed unused StyledChatUploadedFileError styled component |
e2e_playwright/st_chat_input_test.py |
Updated tests to verify error tooltips appear on hover instead of inline; added tooltip visibility assertions |
e2e_playwright/__snapshots__/linux/st_chat_input_test/*.png |
Added new snapshot files for error tooltip appearance and updated error file chip snapshots |
frontend/lib/src/components/widgets/ChatInput/fileUpload/ChatUploadedFile.tsx
Show resolved
Hide resolved
fdd0f59 to
e357f7d
Compare
frontend/lib/src/components/widgets/ChatInput/fileUpload/ChatUploadedFile.test.tsx
Outdated
Show resolved
Hide resolved
e357f7d to
d7cff11
Compare
|
@cursor review |
SummaryThis PR replaces inline error messages with tooltips for file upload errors in Key changes:
Code QualityThe code is well-structured and follows the established patterns in the Streamlit codebase: ✅ React best practices followed:
✅ Excellent accessibility implementation:
✅ Clean code removal:
✅ Proper eslint handling:
Minor observation:
Test CoverageFrontend Unit Tests (ChatUploadedFile.test.tsx): ✅ Comprehensive test coverage including:
The tests follow RTL best practices:
E2E Tests (st_chat_input_test.py): ✅ Properly updated to test new tooltip behavior:
The E2E tests follow best practices from
Backwards Compatibility✅ No breaking changes. This is a purely visual/UX change:
Users will not need to modify any code to adopt this change. Security & Risk✅ No security concerns identified:
Low regression risk:
RecommendationsThe implementation is solid. A few optional suggestions for future consideration:
VerdictAPPROVED: This is a well-implemented UX improvement that follows React best practices, includes comprehensive accessibility support, and has thorough test coverage at both unit and E2E levels. The code is clean, well-documented, and backwards compatible. This is an automated AI review. Please verify the feedback and use your judgment. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
✅ Bugbot reviewed your changes and found no bugs!
| {isError && ( | ||
| <StyledVisuallyHidden id={errorId} role="alert"> | ||
| Error: {errorMessage} | ||
| </StyledVisuallyHidden> | ||
| )} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nitpick: Wouldn't it be possible to handle this from within Tooltip by making the tooltip content always accessible? And isn't there a way to directly attach this to the tooltip DOM element, or is there no DOM element related to the tooltip if it's not rendered? cc @sfc-gh-bnisco for expertise on accessibility.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for flagging, I had to do some investigation on this one.
To directly answer Lukas's comments: We could update the Tooltip API to ensure it always exists in the DOM, but that would be a change across every usage of Tooltip, and may cause unexpected side-effects without auditing every usage. Generally speaking, most component libraries only render Tooltip instances when they are triggered, so right now our behavior is aligned with that and we probably don't want to change that.
It looks like the main thing here is that this uses role="alert", which is not a pattern we have used much internally, but is a legitimate usecase here. Since the Tooltip DOM element doesn't exist until it's triggered, there is nothing that could be used in aria-describedby with current implementation, hence the addition of this StyledVisuallyHidden span. This seems reasonable to me.
I have a different piece of a11y feedback, but will put in a separate comment.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for the discussion guys. I came to the same conclusion Bob did about the tooltip not being present until hover putting us in a sort of catch 22 situation when trying to solve this globally. I didn't think of the idea where we change tooltip to be present in the DOM always, but agree that involves more risk.
lukasmasuch
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM 👍 the accessibility aspect might need another check
| {isError && ( | ||
| <StyledVisuallyHidden id={errorId} role="alert"> | ||
| Error: {errorMessage} | ||
| </StyledVisuallyHidden> | ||
| )} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for flagging, I had to do some investigation on this one.
To directly answer Lukas's comments: We could update the Tooltip API to ensure it always exists in the DOM, but that would be a change across every usage of Tooltip, and may cause unexpected side-effects without auditing every usage. Generally speaking, most component libraries only render Tooltip instances when they are triggered, so right now our behavior is aligned with that and we probably don't want to change that.
It looks like the main thing here is that this uses role="alert", which is not a pattern we have used much internally, but is a legitimate usecase here. Since the Tooltip DOM element doesn't exist until it's triggered, there is nothing that could be used in aria-describedby with current implementation, hence the addition of this StyledVisuallyHidden span. This seems reasonable to me.
I have a different piece of a11y feedback, but will put in a separate comment.
frontend/lib/src/components/widgets/ChatInput/fileUpload/ChatUploadedFile.tsx
Outdated
Show resolved
Hide resolved
Kapture.2026-01-09.at.10.00.47.mp4question: Why does clicking (or hitting enter with keyboard when focused) on this element cause the error state to go away? |
d7cff11 to
a419335
Compare
The aria-label now always shows filename and size (not error message) to avoid screen readers double-announcing the error. Error is conveyed via aria-describedby linking to the visually hidden error element.

Describe your changes
Changed file upload error messages in chat input to display as tooltips instead of inline text. This improves the UI by:
Screenshot or video (only for visual changes)
Designs
Actual
Note: still need clarity on the x icon hover colors so will have that in a separate PR with the error text colors too.
Testing Plan
Contribution License Agreement
By submitting this pull request you agree that all contributions to this project are made under the Apache 2.0 license.