Skip to content

fix(intelligent-assistant): scope PatternFly CSS to chatbot component to prevent dark theme leak#3827

Open
its-mitesh-kumar wants to merge 4 commits into
redhat-developer:mainfrom
its-mitesh-kumar:fix/intelligent-assistant-RHDHBUGS-3473-pf-css-dark-theme-leak
Open

fix(intelligent-assistant): scope PatternFly CSS to chatbot component to prevent dark theme leak#3827
its-mitesh-kumar wants to merge 4 commits into
redhat-developer:mainfrom
its-mitesh-kumar:fix/intelligent-assistant-RHDHBUGS-3473-pf-css-dark-theme-leak

Conversation

@its-mitesh-kumar

@its-mitesh-kumar its-mitesh-kumar commented Jul 18, 2026

Copy link
Copy Markdown
Member

Description

Fixes a dark theme CSS leak (white background) introduced by the @patternfly/react-core upgrade from 6.4.36.6.0.

When it started breaking

The issue was introduced in commit ddd4f254f ("updating patternfly version", July 9, 2026) which bumped @patternfly/react-core from 6.4.3 to 6.6.0. It was working fine on 6.4.3.

Why it broke

PatternFly 6.6.0 added container-type: inline-size to the <html> element in base-no-reset.css. Since LightspeedChatContainer.tsx imports this CSS file at the module level, and it was statically imported by both index.tsx and legacy.ts, the CSS loaded eagerly at plugin registration time — on every page, regardless of whether the chatbot was visible.

The container-type: inline-size on <html> changes how it behaves as a containing block, breaking the <body> height calculation (body.scrollHeight < viewport height). The gap below the body reveals the browser's default white canvas, which appears as a white background leak in dark mode.

Additionally, the AppDrawerContentBlueprint mounts LightspeedChatContainer on all pages (persistent drawer), so the CSS is always active once loaded.

The fix (3 parts)

  1. Lazy loading — Created LightspeedChatContainerLazy.tsx using React.lazy() to defer CSS loading until the component actually renders, rather than at module parse/registration time. Updated imports in index.tsx, legacy.ts, and LightspeedDrawerProvider.tsx.

  2. container-type override — Added a useLayoutEffect that sets document.documentElement.style.containerType = 'normal' on mount, counteracting PatternFly 6.6.0's container-type: inline-size which breaks body height.

  3. No cleanup functions — The useLayoutEffect hooks intentionally omit cleanup (return () => { ... }). In React StrictMode, cleanup fires during remount cycles which would temporarily remove pf-v6-theme-dark and reset container-type, causing a brief flash of white/light theme. Since PatternFly CSS is permanently in the DOM once loaded, the overrides must also be permanent.

Fixed

  • RHDHBUGS-3473 — PatternFly base-no-reset.css leaks white background into Backstage dark theme

Upstream Issue : patternfly/patternfly-react#12568

UI befor change

S_ 2026-07-18 at 2 20 26 PM (2)

UI after changes

S_.2026-07-18.at.8.43.10.PM.mov

Test Plan

  • Start the dev app: cd workspaces/intelligent-assistant && yarn start
  • Switch to RHDH Dark theme via Settings > Appearance > Theme
  • Navigate to any page (e.g., Settings)
  • Verify no white background area below the main page content
  • Open the chatbot drawer
  • Verify the chatbot and drawer backgrounds match the dark theme
  • Navigate away from the chatbot page (e.g., back to Settings)
  • Verify the white background does NOT reappear
  • Switch back to light theme and verify chatbot still renders correctly

Checklist

  • A changeset describing the change and affected packages. (more info)
  • Tests for new functionality and regression tests for bug fixes
  • Screenshots attached (for UI changes)

… to prevent dark theme leak

Fixes: https://redhat.atlassian.net/browse/RHDHBUGS-3473
Signed-off-by: its-mitesh-kumar <itsmiteshkumar98@gmail.com>
@rhdh-gh-app

rhdh-gh-app Bot commented Jul 18, 2026

Copy link
Copy Markdown

Changed Packages

Package Name Package Path Changeset Bump Current Version
@red-hat-developer-hub/backstage-plugin-intelligent-assistant workspaces/intelligent-assistant/plugins/intelligent-assistant patch v3.0.3

@its-mitesh-kumar

Copy link
Copy Markdown
Member Author

/fs-review

@fullsend-ai-review

fullsend-ai-review Bot commented Jul 18, 2026

Copy link
Copy Markdown

🤖 Finished Review · ✅ Success · Started 4:59 AM UTC · Completed 5:05 AM UTC
Commit: 73c1162 · View workflow run →

@codecov

codecov Bot commented Jul 18, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 63.63636% with 4 lines in your changes missing coverage. Please review.
✅ Project coverage is 56.26%. Comparing base (73c1162) to head (c5e2f22).
⚠️ Report is 9 commits behind head on main.
✅ All tests successful. No failed tests found.

Additional details and impacted files
@@            Coverage Diff             @@
##             main    #3827      +/-   ##
==========================================
- Coverage   56.26%   56.26%   -0.01%     
==========================================
  Files        2499     2500       +1     
  Lines       96058    96064       +6     
  Branches    26710    26710              
==========================================
+ Hits        54048    54050       +2     
- Misses      41683    41687       +4     
  Partials      327      327              
Flag Coverage Δ *Carryforward flag
adoption-insights 83.70% <ø> (ø) Carriedforward from 45dce79
ai-integrations 69.00% <ø> (ø) Carriedforward from 45dce79
app-defaults 69.79% <ø> (ø) Carriedforward from 45dce79
augment 46.39% <ø> (ø) Carriedforward from 45dce79
boost 73.13% <ø> (ø) Carriedforward from 45dce79
bulk-import 72.46% <ø> (ø) Carriedforward from 45dce79
cost-management 14.10% <ø> (ø) Carriedforward from 45dce79
dcm 61.81% <ø> (ø) Carriedforward from 45dce79
extensions 61.53% <ø> (ø) Carriedforward from 45dce79
global-floating-action-button 71.18% <ø> (ø) Carriedforward from 45dce79
global-header 59.71% <ø> (ø) Carriedforward from 45dce79
homepage 50.30% <ø> (ø) Carriedforward from 45dce79
install-dynamic-plugins 56.77% <ø> (ø) Carriedforward from 45dce79
intelligent-assistant 68.97% <63.63%> (-0.04%) ⬇️
konflux 91.49% <ø> (ø) Carriedforward from 45dce79
lightspeed 69.02% <ø> (ø) Carriedforward from 45dce79
mcp-integrations 85.46% <ø> (ø) Carriedforward from 45dce79
orchestrator 53.74% <ø> (ø) Carriedforward from 45dce79
quickstart 65.63% <ø> (ø) Carriedforward from 45dce79
sandbox 79.56% <ø> (ø) Carriedforward from 45dce79
scorecard 82.96% <ø> (ø) Carriedforward from 45dce79
theme 61.26% <ø> (ø) Carriedforward from 45dce79
translations 7.25% <ø> (ø) Carriedforward from 45dce79
x2a 78.68% <ø> (ø) Carriedforward from 45dce79

*This pull request uses carry forward flags. Click here to find out more.


Continue to review full report in Codecov by Harness.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 73c1162...c5e2f22. Read the comment docs.

🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@fullsend-ai-review

fullsend-ai-review Bot commented Jul 18, 2026

Copy link
Copy Markdown

Review

Reason: stale-head

The review agent reviewed commit 45dce79fe622fcb498ef3be80f0b714e808c9656 but the PR HEAD is now c5e2f22105abde5a5f41f4ccd87e569c5b76383b. This review was discarded to avoid approving unreviewed code.

Previous run

Review — approve

Scope: workspaces/intelligent-assistant · 5 files · +12 / −14

Summary

This PR fixes RHDHBUGS-3473 — PatternFly's base-no-reset.css leaked :root CSS custom properties (white background values) into the Backstage dark theme. The fix has two parts:

  1. CSS import relocation — moves @patternfly/react-core/dist/styles/base-no-reset.css and @patternfly/chatbot/dist/css/main.css out of the three plugin entry points (index.tsx, legacy.ts, plugin.ts) and into LightspeedChatContainer.tsx, colocating them with the component that actually consumes PatternFly.

  2. useEffectuseLayoutEffect — the dark theme class (pf-v6-theme-dark) is now applied synchronously after DOM mutations but before paint, preventing the white background flash on dark themes.

Findings

1. CSS imports still load eagerly through static import chains — low

File: workspaces/intelligent-assistant/plugins/intelligent-assistant/src/components/LightspeedChatContainer.tsx

The PR description states that moving CSS imports into the component defers them until the component renders. In practice, LightspeedChatContainer.tsx is statically imported by both index.tsx (line 47: import { LightspeedChatContainer as LightspeedChatContainerElement } from './components/LightspeedChatContainer') and re-exported by legacy.ts (line 33: export { LightspeedChatContainer } from './components/LightspeedChatContainer'). Since CSS imports are module-level side effects, they execute when any module in the static import chain is evaluated — which is plugin registration time for both entry points.

The CSS is only truly deferred for the lazy path in plugin.ts (via createComponentExtension({ component: { lazy: () => import('./components/LightspeedChatContainer')... } })).

This does not block the fix — the useLayoutEffect change is the primary mechanism that prevents the visible white flash, and it works correctly regardless of CSS loading timing. The colocation is still a code-hygiene improvement. But if full CSS deferral is desired in a follow-up, index.tsx would need a dynamic import() instead of the static import, and legacy.ts would need to re-export the lazy extension from plugin.ts rather than the raw component.

2. useLayoutEffect for global DOM mutation is correct here — info (suppressed)

useLayoutEffect is the right hook for synchronous DOM mutations that must happen before paint. Since Backstage is a client-side SPA (no SSR), there are no SSR warning concerns. The existing codebase already uses useLayoutEffect in LightSpeedChat.tsx for similar layout-sensitive operations.

Verdict

Approve. The useLayoutEffect change correctly eliminates the dark theme white background flash. The CSS import relocation improves code organization. The changeset is present and properly scoped. The change is minimal, well-targeted, and does not alter any public API surface.

*/

import { useEffect, useMemo, useState } from 'react';
import '@patternfly/react-core/dist/styles/base-no-reset.css';

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

[low] correctness

CSS imports in LightspeedChatContainer.tsx still load eagerly through static import chains in index.tsx (line 47) and legacy.ts (line 33). The CSS deferral benefit described in the PR only applies to the lazy path in plugin.ts. The useLayoutEffect change is the actual effective fix for the white flash.

Suggested fix: For full CSS deferral, convert the static import in index.tsx to a dynamic import() and have legacy.ts re-export the lazy extension from plugin.ts instead of the raw component.

@fullsend-ai-review fullsend-ai-review Bot added the ready-for-merge All reviewers approved — ready to merge label Jul 18, 2026
Signed-off-by: its-mitesh-kumar <itsmiteshkumar98@gmail.com>
Signed-off-by: its-mitesh-kumar <itsmiteshkumar98@gmail.com>
@its-mitesh-kumar

Copy link
Copy Markdown
Member Author

/fs-review

@fullsend-ai-review

fullsend-ai-review Bot commented Jul 18, 2026

Copy link
Copy Markdown

🤖 Finished Review · ✅ Success · Started 3:34 PM UTC · Completed 3:49 PM UTC
Commit: cf89b92 · View workflow run →

…der test

Update jest.mock path from '../LightspeedChatContainer' to
'../LightspeedChatContainerLazy' to match the updated import in
LightspeedDrawerProvider.tsx after the lazy wrapper refactor.

Signed-off-by: its-mitesh-kumar <itsmiteshkumar98@gmail.com>
Co-authored-by: Cursor <cursoragent@cursor.com>
@sonarqubecloud

Copy link
Copy Markdown

@fullsend-ai-review

Copy link
Copy Markdown

/fs-review

@its-mitesh-kumar

Copy link
Copy Markdown
Member Author

/fs-review

@its-mitesh-kumar

Copy link
Copy Markdown
Member Author

I have also raised the upstream issue : patternfly/patternfly-react#12568

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

ready-for-merge All reviewers approved — ready to merge workspace/intelligent-assistant

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant