Files
cinny/LOTUS_BUGS.md
T
jared e9a970a75b
CI / Build & Quality Checks (push) Successful in 10m22s
Trigger Desktop Build / trigger (push) Successful in 7s
fix: settings dropdowns, background animations, ringing, avatar decorations
Settings dropdowns (Bug #3):
- Add reusable SettingsSelect component using Menu+PopOut+FocusTrap — exact
  same pattern as Message Layout, so all dropdowns look consistent
- Replace raw <select> for Seasonal Theme, UI Font, AFK Timeout, and
  Join & Leave Sounds with SettingsSelect

Animated chat backgrounds bleeding onto content (Bug #6 / #7):
- Remove filter:brightness() and opacity animations from chatBackground.ts
  (animRainGlowKeyframe, animGridBrightnessKeyframe, animFirefliesGlowKeyframe,
  animFirefliesBlinkKeyframe). These were applied to the Page element which
  caused ALL descendants (messages, composer) to flash in sync.
  Also created a CSS stacking context on Page that pushed SeasonalEffect
  (position:fixed; z-index:9997) behind the animated background layer.
- Only backgroundPosition / backgroundSize animations remain — safe, do not
  affect descendants, and do not create stacking contexts.
- Remove now-unused animation keyframe imports from chatBackground.ts.

Voice ringing in persistent rooms (Bug #5):
- Narrow the ringing condition from (Invite|Knock|Restricted) to only Invite,
  matching exactly the rooms where the call button is visible.
- Add room.isCallRoom() early-exit so m.join_rule:call rooms never ring.

Avatar decoration images not loading (Bug #8):
- Change loading="lazy" → loading="eager" in DecorationPreviewCell.
  Lazy loading does not reliably trigger for images inside nested overflow
  scroll containers (the settings panel scroll area), so images never loaded.

Docs: LOTUS_BUGS.md updated with root cause and resolution for all 5 new bugs.
Docs: LOTUS_TODO.md adds P5-35/P5-36 (deferred desktop notification/jump list).

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-06-14 12:20:47 -04:00

9.6 KiB
Raw Blame History

Lotus Chat — Bug Report & Technical Audit

Date: June 2026

This document tracks identified bugs, edge cases, and architectural discrepancies found during the audit of the Lotus Chat codebase. Recommended fixes are provided for each item.


🛡️ Critical Security & Privacy Regressions

File: src/app/features/room/MediaGallery.tsx (Line 855) Status: CRITICAL

  • Issue: The "Download" button in the Files tab uses mxcUrlToHttp directly and clicks an <a> link.
  • Impact: In encrypted rooms, this downloads the encrypted ciphertext rather than the decrypted file. Users cannot open the downloaded files.
  • Recommended Fix:
    1. Check if the event is encrypted.
    2. If encrypted, use the decryptAttachment logic (similar to useDecryptedMediaUrl) to decrypt the file in memory.
    3. Use file-saver or a Blob URL to trigger the download of the decrypted plaintext.

2. Privacy Leak in URL Previews

File: src/app/components/url-preview/UrlPreviewCard.tsx (Line 1655) Status: PRIVACY RISK

  • Issue: Generic URL preview cards fetch favicons directly from https://www.google.com/s2/favicons?domain=....
  • Impact: This leaks the user's browsing/chat activity (domains of links they see) to Google. It bypasses the "proxied through Matrix" privacy standard.
  • Recommended Fix: Use the proxy URL returned by the Matrix /_matrix/media/v3/preview_url endpoint instead of contacting Google directly.

🚩 Functional & Logic Bugs

1. Presence Updater Reverts Status Updates

File: src/app/hooks/usePresenceUpdater.ts (Line 20) Status: RESOLVED (June 2026)

  • Issue: The storedStatus variable was captured once when the useEffect started.
  • Impact: If a user updated their status message in Profile Settings, the hook would continue broadcasting the old message on every activity event, silently reverting the change.
  • Fix Applied: Replaced the single localStorage.getItem read with a readStatus() function called inside every setOnline and setUnavailable invocation, ensuring the current value is always used.

2. Audio Playback Rate Reset

File: src/app/components/message/content/AudioContent.tsx (Line 97) Status: UX Bug

  • Issue: The playbackRate is set in a useEffect that only depends on [playbackSpeed].
  • Impact: If a user selects a playback speed before the audio blob has finished loading, the <audio> element may reset its rate to 1.0 once the <source> is added.
  • Recommended Fix: Add srcState.data to the useEffect dependencies or set the playbackRate in an onCanPlay handler on the audio element.

3. Room Insights are Static (No Live Updates)

File: src/app/features/room-settings/RoomInsights.tsx (Line 60) Status: Medium Priority

  • Issue: Stats are calculated in a useMemo that only depends on [room].
  • Impact: If new messages arrive while the Insights page is open, the statistics (message counts, top participants, etc.) do not update.
  • Recommended Fix: Add a listener for RoomEvent.Timeline inside the component to trigger a recalculation when new events are added to the room.

4. Incorrect Ringing in Voice Rooms

File: src/app/components/CallEmbedProvider.tsx Status: RESOLVED (June 2026)

  • Issue: Joining a static voice room (Public Space channel) triggered the "Incoming Call" ringing animation and sound.
  • Root Cause: getStateEvent(room, StateEvent.SpaceParent) always returned undefined because m.space.parent events use the parent space's room ID as the state key, not an empty string. The ringing suppression check silently failed.
  • Fix Applied: Replaced getStateEvent with getStateEvents (plural), which returns all events of a given type regardless of state key. A room with any m.space.parent event is correctly identified as a space channel and suppresses ringing.

🎨 UI/UX & Visual Consistency

1. Hardcoded Primary Color in Polls

File: src/app/components/message/content/PollContent.tsx (Line 245) Status: TDS Violation

  • Issue: Uses rgba(var(--mx-primary-rgb, 0,132,255), ...) for selected options and borders.
  • Impact: Polls look like standard Cinny and ignore the Lotus Terminal Design System (TDS) colors.
  • Recommended Fix: Use var(--lt-accent-cyan) or the primary theme accent color.

2. Inaccessible Room Menu on Mobile

File: src/app/features/room-nav/RoomNavItem.tsx (Line 643) Status: MOBILE BUG

  • Issue: The room menu icon (VerticalDots) is hidden on mobile because hover is never active.
  • Impact: Mobile users cannot access room settings, mark as read, or leave rooms from the sidebar.
  • Recommended Fix: Ensure the menu button is visible on mobile for the active room or provide an alternative trigger.

3. Inconsistent Settings Dropdown Styling

File: src/app/features/settings/general/General.tsx Status: RESOLVED (June 2026)

  • Issue: The dropdowns for "Join & Leave Sounds", "UI Font", and "Seasonal Theme" used raw HTML <select> elements, which render differently from the custom-styled Menu+PopOut used for "Message Layout" and other settings.
  • Fix Applied: All three raw <select> elements replaced with a reusable SettingsSelect component using the Menu+PopOut+FocusTrap pattern consistent with the rest of the settings UI.

4. No Camera Focus During Screenshare

File: src/app/features/call/CallControls.tsx Status: UX Bug — blocked by Element Call internals

  • Issue: When someone is screensharing and another participant turns on their camera, there is no way to switch the primary display to the camera or go fullscreen on it.
  • Root Cause: Element Call's spotlight/layout is controlled internally by EC. Lotus Chat injects the call iframe and cannot easily override EC's participant tile behavior without forking the EC widget.
  • Recommended Fix: Implement a "Pin/Focus" toggle on participant tiles that overrides the automatic screenshare spotlight — requires EC upstream changes or a custom message bridge.

5. Ringing Modal Fires in Persistent Voice Rooms

File: src/app/components/CallEmbedProvider.tsx (line 337342) Status: RESOLVED (June 2026)

  • Issue: Joining a persistent voice room (not a DM or transient group call) showed the incoming call ringing modal and animation.
  • Root Cause: The isPrivateGroup condition included JoinRule.Restricted and JoinRule.Knock rooms. Lotus Guild voice rooms are Restricted join-rule rooms. Their m.space.parent state event was being checked but some rooms were set up with only the space-side m.space.child relationship, leaving no m.space.parent on the room itself — so they passed as isPrivateGroup and triggered ringing.
  • Fix Applied: Narrowed isPrivateGroup to only JoinRule.Invite to match the exact set of rooms where the call button is shown. Also added room.isCallRoom() early-exit so rooms with m.join_rule.call type never ring.

6. Animated Chat Backgrounds Affect Message Content

File: src/app/features/lotus/chatBackground.ts Status: RESOLVED (June 2026)

  • Issue: Animated backgrounds that use filter: brightness() or opacity animations (Digital Rain glow, Grid Pulse brightness, Fireflies glow/blink) applied those effects to the entire <Page> element, causing all message content and the composer to flash/flicker in sync with the animation.
  • Root Cause: filter and opacity CSS properties affect an element AND all its descendants. Applying these as part of the animation shorthand on the Page container made them "inherited" visually by everything inside the room view.
  • Side Effect: filter animation also created a CSS stacking context on Page, which pushed Seasonal Theme overlays (position:fixed; z-index:9997) behind the Page compositor layer.
  • Fix Applied: Removed animRainGlowKeyframe, animGridBrightnessKeyframe, animFirefliesGlowKeyframe, and animFirefliesBlinkKeyframe from chatBackground.ts. Only backgroundPosition / backgroundSize animations remain — these are safe and do not affect descendants or create stacking contexts.

7. Seasonal Themes Display Behind Chat Background

File: src/app/components/seasonal/SeasonalEffect.tsx Status: RESOLVED (June 2026) — root cause was Bug #6

  • Issue: Seasonal theme overlays (position:fixed; z-index:9997) appeared behind animated chat backgrounds.
  • Root Cause: The filter animation on <Page> created a CSS stacking context, causing Page's GPU compositing layer to render above the fixed-position seasonal overlay in some browsers. Removing the filter animations (Bug #6 fix) resolves the stacking context issue.
  • Fix Applied: See Bug #6. No additional changes to SeasonalEffect required.

8. Avatar Decoration Images Not Rendering in Settings

File: src/app/features/settings/account/ProfileDecoration.tsx Status: RESOLVED (June 2026)

  • Issue: Under Settings → Account → Avatar Decoration, no decoration images were visible.
  • Root Cause: The DecorationPreviewCell used loading="lazy" on decoration images. The browser's lazy-loading algorithm determines image visibility from the viewport, but the decoration grid is inside a nested overflowY: auto scroll container inside a settings panel — the browser did not correctly detect these images as near the viewport and never triggered them to load.
  • Fix Applied: Changed loading="lazy" to loading="eager" in DecorationPreviewCell. The settings panel is user-initiated, so eager loading is appropriate.