Skip to content

Commit 499eb40

Browse files
authored
fix(web): layer plugin modal above account chrome (#6912)
1 parent 932c9c5 commit 499eb40

2 files changed

Lines changed: 14 additions & 3 deletions

File tree

apps/web/src/components/PluginsView.tsx

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import {
99
type KeyboardEvent,
1010
type SetStateAction,
1111
} from 'react';
12+
import { createPortal } from 'react-dom';
1213
import { Dialog } from '@open-design/components';
1314
import {
1415
PLUGIN_SHARE_ACTION_PLUGIN_IDS,
@@ -3215,7 +3216,7 @@ function AvailablePluginDetailsModal({
32153216
});
32163217
}
32173218

3218-
return (
3219+
const modal = (
32193220
<div
32203221
className="plugin-details-modal-backdrop"
32213222
role="dialog"
@@ -3519,6 +3520,9 @@ function AvailablePluginDetailsModal({
35193520
</div>
35203521
</div>
35213522
);
3523+
3524+
if (typeof document === 'undefined') return modal;
3525+
return createPortal(modal, document.body);
35223526
}
35233527

35243528
function SourcesPanel({

apps/web/tests/components/ExtensionsMarketplace.plugin-detail-entry.test.tsx

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -171,8 +171,8 @@ describe('ExtensionsMarketplace installed plugin detail entry', () => {
171171
expect(screen.queryByTestId('plugin-detail')).toBeNull();
172172
});
173173

174-
it('keeps an uninstalled Community card in the existing install modal', async () => {
175-
renderHarness();
174+
it('keeps an uninstalled Community card in a root-level install modal', async () => {
175+
const { container } = renderHarness();
176176

177177
fireEvent.click(
178178
await screen.findByTestId(
@@ -183,6 +183,13 @@ describe('ExtensionsMarketplace installed plugin detail entry', () => {
183183
const modal = await screen.findByTestId('plugins-available-details-modal');
184184
expect(window.location.pathname).toBe('/plugins');
185185
expect(screen.queryByTestId('plugin-detail')).toBeNull();
186+
// The top-right account cluster is also portalled to <body>. Keeping the
187+
// scrim inside the marketplace stacking context lets that cluster paint
188+
// above the backdrop and escape its blur.
189+
expect(modal.parentElement).toBe(document.body);
190+
expect(
191+
container.querySelector('[data-testid="plugins-available-details-modal"]'),
192+
).toBeNull();
186193
expect(within(modal).getByText('Community Plugin Kit')).toBeTruthy();
187194
expect(
188195
within(modal).getByTestId(

0 commit comments

Comments
 (0)