Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
42 commits
Select commit Hold shift + click to select a range
d9894b2
Upgrade LG modal packages
kraenhansen Dec 18, 2025
8096983
Fix Modal to adopt LG Modal v20
kraenhansen Sep 30, 2025
1a79dee
Fix connection-form to work around LG Modal v20
kraenhansen Sep 30, 2025
baf002b
Update generative-ai to adopt marketing-modal v7
kraenhansen Sep 30, 2025
9fc6af6
Fix compass-import-export to work around LG modal v20
kraenhansen Sep 30, 2025
e1855b4
Update compass-welcome to adopt marketing-modal v7
kraenhansen Nov 5, 2025
c5274cb
Update compass-explain-plan to LG Modal v20
kraenhansen Oct 1, 2025
37a6cc7
Fix compass-crud to adopt LG modal v20
kraenhansen Oct 1, 2025
5f418d2
Update compass-schema to LG Modal v20
kraenhansen Oct 1, 2025
65831d9
Add workaround for jsdom missing HTMLDialogElement support
kraenhansen Oct 2, 2025
09eb31d
Update generative-ai to adopt LG modal v20
kraenhansen Oct 7, 2025
cd281f6
Fix fullScreen prop on derived Modal
kraenhansen Oct 7, 2025
21f3682
Remove use of deprecated backdropClassName
kraenhansen Oct 7, 2025
aa0f76f
Remove workaround for MarketingModal button disabling
kraenhansen Dec 10, 2025
5cc4946
Fix remaining components tests
kraenhansen Oct 7, 2025
5ae783d
Revert workaround for LG-5593
kraenhansen Oct 8, 2025
669e0cd
Update existing tests to handle dialog elements remaining in the DOM
kraenhansen Nov 5, 2025
e473a04
Update databases-collections to allow immediate removal of the heading
kraenhansen Nov 6, 2025
01c66a3
Update e2e tests to use waitForDisplayed over waitForExist as this is…
kraenhansen Nov 6, 2025
b343940
Update e2e tests removing [role=dialog] from confirm dialog selectors
kraenhansen Nov 7, 2025
3cdb6c7
Update e2e tests to wait for bulk delete modal to disappear
kraenhansen Nov 7, 2025
ad72a99
Update e2e tests to wait for connection form to be non-clickable in a…
kraenhansen Nov 7, 2025
5e5ce3b
Update e2e tests to fix modal regressions
kraenhansen Nov 21, 2025
2778a71
Disable pointer events on a closed modal
kraenhansen Nov 10, 2025
d1fe84b
Disable auto-focus on confirmation modal children by default
kraenhansen Nov 10, 2025
6ab317e
Add new modal specific commands
kraenhansen Nov 11, 2025
70e7015
Update E2E tests to use new modal commands instead of waitForDisplayed
kraenhansen Nov 11, 2025
f839793
Default initialFocus to "null" to avoid breaking existing modals
kraenhansen Nov 12, 2025
cf032a1
Wait for confirm button to show instead of simply expecting it
kraenhansen Nov 17, 2025
bb6ff36
Update FocusMode tests to handle LG Modal v20
kraenhansen Nov 25, 2025
3799746
Update SettingsModal tests to handle LG Modal v20
kraenhansen Nov 25, 2025
7ca774e
Clarify disabling the @typescript-eslint/no-namespace and add a TODO …
kraenhansen Nov 26, 2025
de78fec
Partial revert of ddd6d70dd59fbe8f948ea6e5ef80b6d478bc1eff
kraenhansen Nov 26, 2025
920efc6
Fix auto-focus in bulk update and delete modals
kraenhansen Dec 1, 2025
2f73260
Correcting sizing styles
kraenhansen Dec 9, 2025
c2e5d46
Correcting sizing styles more
kraenhansen Dec 9, 2025
9646d87
Use named imports
kraenhansen Dec 18, 2025
d43fc16
Upgrade confirm-modal package
kraenhansen Dec 18, 2025
dbe7574
Fix useConfirmation's confirmButtonProps types
kraenhansen Dec 18, 2025
9767e4f
Update use of ConfirmationModal
kraenhansen Dec 18, 2025
564fc1e
Set initial focus on cancel (fallback to confirm) button
kraenhansen Dec 18, 2025
6fa377d
Fix package lock
kraenhansen Dec 18, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Update E2E tests to use new modal commands instead of waitForDisplayed
  • Loading branch information
kraenhansen committed Dec 18, 2025
commit 70e70152bf66e0223f7cd568a02fa8d8e4b7da3e
Original file line number Diff line number Diff line change
Expand Up @@ -34,8 +34,7 @@ export async function addCollection(
collectionOptions?: AddCollectionOptions,
screenshotPath?: string
): Promise<void> {
const createModalElement = browser.$(Selectors.CreateCollectionModal);
await createModalElement.waitForDisplayed();
await browser.waitForOpenModal(Selectors.CreateCollectionModal);

await browser.setValueVisible(
Selectors.CreateDatabaseCollectionName,
Expand Down Expand Up @@ -216,5 +215,7 @@ export async function addCollection(
}

await browser.clickVisible(Selectors.CreateCollectionCreateButton);
await createModalElement.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.CreateCollectionModal, {
reverse: true,
});
}
7 changes: 4 additions & 3 deletions packages/compass-e2e-tests/helpers/commands/add-database.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,7 @@ export async function addDatabase(
collectionOptions?: AddCollectionOptions,
screenshotPath?: string
): Promise<void> {
const createModalElement = browser.$(Selectors.CreateDatabaseModal);
await createModalElement.waitForDisplayed();
await browser.waitForOpenModal(Selectors.CreateDatabaseModal);
await browser.setValueVisible(Selectors.CreateDatabaseDatabaseName, dbName);
await browser.setValueVisible(
Selectors.CreateDatabaseCollectionName,
Expand All @@ -25,5 +24,7 @@ export async function addDatabase(
}

await createButton.click();
await createModalElement.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.CreateDatabaseModal, {
reverse: true,
});
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,7 @@ export async function clickConfirmationAction(
) {
await browser.clickVisible(actionButtonSelector);

const confirmationModal = browser.$(Selectors.ConfirmationModal);
await confirmationModal.waitForDisplayed();
await browser.waitForOpenModal(Selectors.ConfirmationModal);

if (confirmationText) {
await browser.setValueVisible(
Expand All @@ -24,5 +23,7 @@ export async function clickConfirmationAction(
}

await browser.clickVisible(Selectors.confirmationModalConfirmButton());
await confirmationModal.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.ConfirmationModal, {
reverse: true,
});
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,11 @@ import * as Selectors from '../selectors';
export async function closeSettingsModal(
browser: CompassBrowser
): Promise<void> {
if (!(await browser.existsEventually(Selectors.SettingsModal))) {
if (!(await browser.isModalEventuallyOpen(Selectors.SettingsModal))) {
return;
}

const settingsModalElement = browser.$(Selectors.SettingsModal);

await settingsModalElement.waitForDisplayed();

await browser.waitForOpenModal(Selectors.SettingsModal);
await browser.clickVisible(Selectors.CloseSettingsModalButton);
await settingsModalElement.waitForDisplayed({
reverse: true,
});
await browser.waitForOpenModal(Selectors.SettingsModal, { reverse: true });
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,13 @@ import * as Selectors from '../selectors';
export async function closeWelcomeModal(
browser: CompassBrowser
): Promise<void> {
if (!(await browser.existsEventually(Selectors.WelcomeModal))) {
if (!(await browser.isModalEventuallyOpen(Selectors.WelcomeModal))) {
return;
}

const welcomeModalElement = browser.$(Selectors.WelcomeModal);
await welcomeModalElement.waitForDisplayed();

await browser.waitForOpenModal(Selectors.WelcomeModal);
await browser.clickVisible(Selectors.CloseWelcomeModalButton);
await welcomeModalElement.waitForDisplayed({
reverse: true,
});
await browser.waitForOpenModal(Selectors.WelcomeModal, { reverse: true });

// By setting a feature after closing the welcome modal we know that
// preferences will have been saved to disk and therefore showedNetworkOptIn
Expand Down
10 changes: 3 additions & 7 deletions packages/compass-e2e-tests/helpers/commands/connect-form.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,11 @@ import { getConnectionTitle } from '@mongodb-js/connection-info';
const debug = Debug('compass-e2e-tests');

export async function resetConnectForm(browser: CompassBrowser): Promise<void> {
if (await browser.$(Selectors.ConnectionModal).isDisplayed()) {
if (await browser.isModalOpen(Selectors.ConnectionModal)) {
await browser.clickVisible(Selectors.ConnectionModalCloseButton);
}
await browser
.$(Selectors.ConnectionModal)
.waitForClickable({ reverse: true });

await browser.waitForOpenModal(Selectors.ConnectionModal, { reverse: true });
await browser.clickVisible(Selectors.SidebarNewConnectionButton);

const connectionTitleSelector = Selectors.ConnectionModalTitle;
Expand Down Expand Up @@ -919,9 +917,7 @@ export async function saveConnection(
): Promise<void> {
await browser.setConnectFormState(state);
await browser.clickVisible(Selectors.ConnectionModalSaveButton);
await browser
.$(Selectors.ConnectionModal)
.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.ConnectionModal, { reverse: true });
}

let screenshotCounter = 0;
Expand Down
6 changes: 2 additions & 4 deletions packages/compass-e2e-tests/helpers/commands/connect.ts
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,7 @@ export async function connectWithConnectionString(

// if the modal is still animating away when we're connecting again, things
// are going to get confused
await browser
.$(Selectors.ConnectionModal)
.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.ConnectionModal, { reverse: true });

// if a connection with this name already exists, remove it otherwise we'll
// add a duplicate and things will get complicated fast
Expand All @@ -77,7 +75,7 @@ export async function connectWithConnectionString(
}

await browser.clickVisible(Selectors.SidebarNewConnectionButton);
await browser.$(Selectors.ConnectionModal).waitForDisplayed();
await browser.waitForOpenModal(Selectors.ConnectionModal);

await browser.setValueVisible(
Selectors.ConnectionFormStringInput,
Expand Down
6 changes: 3 additions & 3 deletions packages/compass-e2e-tests/helpers/commands/create-index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,8 @@ export async function createIndex(
} else {
await browser.clickVisible(Selectors.CreateIndexButton);
}
const createModal = browser.$(Selectors.CreateIndexModal);
await createModal.waitForDisplayed();

await browser.waitForOpenModal(Selectors.CreateIndexModal);

// Select / type field name
await browser.setComboBoxValue(
Expand Down Expand Up @@ -114,7 +114,7 @@ export async function createIndex(
await browser.clickVisible(Selectors.CreateIndexConfirmButton);

// Assert that modal goes away
await createModal.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.CreateIndexModal, { reverse: true });

// Assert that index does come in table
const indexComponentSelector = Selectors.indexComponent(indexName);
Expand Down
5 changes: 2 additions & 3 deletions packages/compass-e2e-tests/helpers/commands/drop-index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,7 @@ export async function dropIndex(
`${indexComponentSelector} ${Selectors.IndexesTableDropIndexButton}`
);

const dropModal = browser.$(Selectors.DropIndexModal);
await dropModal.waitForDisplayed();
await browser.waitForOpenModal(Selectors.DropIndexModal);

await browser.setValueVisible(
Selectors.DropIndexModalConfirmNameInput,
Expand All @@ -29,7 +28,7 @@ export async function dropIndex(

await browser.clickVisible(Selectors.DropIndexModalConfirmButton);

await dropModal.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.DropIndexModal, { reverse: true });

await indexComponent.waitForDisplayed({ reverse: true });
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,7 @@ export async function dropNamespace(
browser: CompassBrowser,
collectionName: string
): Promise<void> {
const dropModalElement = browser.$(Selectors.DropNamespaceModal);
await dropModalElement.waitForDisplayed();
await browser.waitForOpenModal(Selectors.DropNamespaceModal);
await browser.setValueVisible(
Selectors.DropNamespaceConfirmNameInput,
collectionName
Expand All @@ -15,6 +14,9 @@ export async function dropNamespace(
await confirmButton.waitForEnabled();

await confirmButton.click();
await browser.waitForOpenModal(Selectors.DropNamespaceModal, {
reverse: true,
});

const successToast = browser.$(Selectors.DropNamespaceSuccessToast);
await successToast.waitForDisplayed();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,7 @@ export async function exportToLanguage(
language: string,
options?: ExportToLanguageOptions
): Promise<string> {
const exportModal = browser.$(Selectors.ExportToLanguageModal);
await exportModal.waitForDisplayed();
await browser.waitForOpenModal(Selectors.ExportToLanguageModal);

// pick the language
await browser.waitUntil(async () => {
Expand Down Expand Up @@ -65,7 +64,9 @@ export async function exportToLanguage(

// close the modal again
await browser.clickVisible(Selectors.ExportToLanguageCloseButton);
await exportModal.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.ExportToLanguageModal, {
reverse: true,
});

// normalize copied text so that it's the same for all platforms
return text.replace(/\r\n/g, '\n').replace(/\n+/g, '\n');
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,17 +10,19 @@ export async function hideVisibleModal(browser: CompassBrowser): Promise<void> {
// the same time we're trying to close the modal, then make it error out
// quickly so it can be ignored and we move on.

if (await browser.$(Selectors.LGModal).isDisplayed()) {
// close any modals that might be in the way
const waitOptions = { timeout: 2_000 };
/* eslint-disable-next-line @typescript-eslint/await-thenable -- WebdriverIO chainable promise array should be awaited */
const openModals = await browser.getOpenModals(Selectors.LGModal);
for (const modal of openModals) {
try {
await browser.clickVisible(Selectors.LGModalClose, waitOptions);
await browser
.$(Selectors.LGModal)
.waitForDisplayed({ reverse: true, ...waitOptions });
await browser.clickVisible(browser.$(modal).$(Selectors.LGModalClose), {
timeout: 2_000,
});
} catch (err) {
// if the modal disappears by itself in the meantime, that's fine
debug('ignoring', err);
debug('ignoring', err instanceof Error ? err.stack : err);
}
}
await browser.waitForOpenModal(Selectors.LGModal, {
reverse: true,
});
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ export async function isModalOpen(
browser: CompassBrowser,
selector: string = Selectors.LGModal
): Promise<boolean> {
/* eslint-disable-next-line @typescript-eslint/await-thenable -- WebdriverIO chainable promise array should be awaited */
const modals = await browser.getOpenModals(selector);
const count = await modals.length;
return count > 0;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,7 @@ export async function openSettingsModal(
require('electron').ipcRenderer.emit('window:show-settings');
});

const settingsModalElement = browser.$(Selectors.SettingsModal);
await settingsModalElement.waitForDisplayed();
await browser.waitForOpenModal(Selectors.SettingsModal);
if (tab) {
await browser.clickVisible(Selectors.SettingsModalTabSelector(tab));
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,8 +34,7 @@ export async function saveAggregationPipeline(
await browser.clickVisible(Selectors.SavePipelineSaveAsAction);

// wait for the modal to appear
const savePipelineModal = browser.$(Selectors.SavePipelineModal);
await savePipelineModal.waitForDisplayed();
await browser.waitForOpenModal(Selectors.SavePipelineModal);

// set aggregation name
await browser.waitForAnimations(Selectors.SavePipelineNameInput);
Expand All @@ -49,7 +48,9 @@ export async function saveAggregationPipeline(
await createButton.click();

// wait for the modal to disappear
await savePipelineModal.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.SavePipelineModal, {
reverse: true,
});

// Wait for the aggregation's name to be displayed.
await browser.waitForAnimations(Selectors.AggregationPipelineName);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,5 @@ export async function saveFavorite(
});

await browser.clickVisible(Selectors.ConnectionModalSaveButton);
await browser
.$(Selectors.ConnectionModal)
.waitForDisplayed({ reverse: true });
return;
await browser.waitForOpenModal(Selectors.ConnectionModal, { reverse: true });
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,7 @@ export async function tryToInsertDocument(
await browser.clickVisible(Selectors.InsertDocumentOption);

// wait for the modal to appear
const insertDialog = browser.$(Selectors.InsertDialog);
await insertDialog.waitForDisplayed();
await browser.waitForOpenModal(Selectors.InsertDialog);

if (document) {
// set the text in the editor
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ export async function waitForOpenModal(
): Promise<void> {
await browser.waitUntil(
async () => {
/* eslint-disable-next-line @typescript-eslint/await-thenable -- WebdriverIO chainable promise array should be awaited */
const modals = await browser.getOpenModals(selector);
Copy link
Collaborator

Choose a reason for hiding this comment

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

I would expect that if I'm calling waitForOpenModal, I'm only looking for one modals, weird to see that this code is dealing with multiple ones instead of throwing if it got more than one back. Is this some quirk of how leafygreen renders those that forces us to do this? Is it just always adding a new modal on the screen or something instead of re-rendering?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Is this some quirk of how leafygreen renders those that forces us to do this?

The selector is often matching a data-testid which is put on the dialog element, which is mounted into the DOM even when the modal is closed. If two components rendering a modal internally is mounted at the same time, multiple elements will match the selector. Waiting for the modal to open then becomes a matter waiting for one of those modals to open.

One alternative I considered was appending a [open] attribute to the selector. I ultimately scrapped that because it felt too brittle. For one, it would not work for selector lists (selectors separated with ,) 🤔 It would be great if WebDriver IO had a way to impose "additional constraints". This is why I'm currently filtering the modals based on their open attribute in getOpenModals:

const open = await element.getAttribute('open');
return open === 'true';

const count = await modals.length;
if (reverse) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,13 +38,13 @@ async function closeTab(

if (autoConfirmTabClose) {
// Tabs in "dirty" state can't be closed without confirmation
if (await browser.$(Selectors.ConfirmTabCloseModal).isExisting()) {
if (await browser.isModalOpen(Selectors.ConfirmTabCloseModal)) {
await browser.clickVisible(
browser.$(Selectors.ConfirmTabCloseModal).$('button=Close tab')
);
await browser
.$(Selectors.ConfirmTabCloseModal)
.waitForDisplayed({ reverse: true });
await browser.waitForOpenModal(Selectors.ConfirmTabCloseModal, {
reverse: true,
});
}
}
return (
Expand Down
Loading