mirror of
https://github.com/element-hq/element-web.git
synced 2025-12-28 07:14:20 +00:00
Fix flaky AppTile tests (#31442)
* Bit of cleanup * Attempts to fix * uncomment * Restructure tests * Better reset * Descrew up tests * fix comment * Remove redundant calls
This commit is contained in:
parent
9faee160e9
commit
d610c3d1ae
@ -122,7 +122,6 @@ export default class ThemeWatcher extends TypedEventEmitter<ThemeWatcherEvent, T
|
||||
return theme;
|
||||
}
|
||||
}
|
||||
logger.log("returning theme value");
|
||||
return SettingsStore.getValue("theme");
|
||||
}
|
||||
|
||||
|
||||
@ -9,7 +9,7 @@ Please see LICENSE files in the repository root for full details.
|
||||
import React from "react";
|
||||
import { Room, type MatrixClient } from "matrix-js-sdk/src/matrix";
|
||||
import { type IWidget, MatrixWidgetType } from "matrix-widget-api";
|
||||
import { act, render, type RenderResult, waitForElementToBeRemoved, waitFor } from "jest-matrix-react";
|
||||
import { act, render, waitForElementToBeRemoved, waitFor } from "jest-matrix-react";
|
||||
import userEvent from "@testing-library/user-event";
|
||||
import {
|
||||
type ApprovalOpts,
|
||||
@ -51,6 +51,8 @@ jest.mock("../../../../../src/stores/OwnProfileStore", () => ({
|
||||
},
|
||||
}));
|
||||
|
||||
const realGetValue = SettingsStore.getValue;
|
||||
|
||||
describe("AppTile", () => {
|
||||
let cli: MatrixClient;
|
||||
let sdkContext: SdkContextClass;
|
||||
@ -106,27 +108,40 @@ describe("AppTile", () => {
|
||||
if (roomId === "r2") return [app2];
|
||||
return [];
|
||||
});
|
||||
});
|
||||
|
||||
afterAll(async () => {
|
||||
jest.restoreAllMocks();
|
||||
});
|
||||
|
||||
beforeEach(async () => {
|
||||
// Do not carry across settings from previous tests
|
||||
SettingsStore.reset();
|
||||
sdkContext = new SdkContextClass();
|
||||
// @ts-ignore
|
||||
await WidgetMessagingStore.instance.onReady();
|
||||
|
||||
// Wake up various stores we rely on
|
||||
WidgetLayoutStore.instance.useUnitTestClient(cli);
|
||||
// @ts-ignore
|
||||
await WidgetLayoutStore.instance.onReady();
|
||||
|
||||
RightPanelStore.instance.useUnitTestClient(cli);
|
||||
// @ts-ignore
|
||||
await RightPanelStore.instance.onReady();
|
||||
});
|
||||
|
||||
beforeEach(async () => {
|
||||
sdkContext = new SdkContextClass();
|
||||
afterEach(async () => {
|
||||
jest.spyOn(SettingsStore, "getValue").mockRestore();
|
||||
// @ts-ignore
|
||||
await WidgetMessagingStore.instance.onReady();
|
||||
await WidgetLayoutStore.instance.onNotReady();
|
||||
// @ts-ignore
|
||||
await RightPanelStore.instance.onNotReady();
|
||||
});
|
||||
|
||||
it("destroys non-persisted right panel widget on room change", async () => {
|
||||
// Set up right panel state
|
||||
const realGetValue = SettingsStore.getValue;
|
||||
const mockSettings = jest.spyOn(SettingsStore, "getValue").mockImplementation((name, roomId) => {
|
||||
jest.spyOn(SettingsStore, "getValue").mockImplementation((name, roomId) => {
|
||||
if (name !== "RightPanel.phases") return realGetValue(name, roomId);
|
||||
if (roomId === "r1") {
|
||||
return {
|
||||
@ -189,8 +204,6 @@ describe("AppTile", () => {
|
||||
|
||||
expect(renderResult.queryByText("Example 1")).not.toBeInTheDocument();
|
||||
expect(ActiveWidgetStore.instance.isLive("1", "r1")).toBe(false);
|
||||
|
||||
mockSettings.mockRestore();
|
||||
});
|
||||
|
||||
it("distinguishes widgets with the same ID in different rooms", async () => {
|
||||
@ -327,50 +340,57 @@ describe("AppTile", () => {
|
||||
expect(ActiveWidgetStore.instance.isLive("1", "r1")).toBe(true);
|
||||
});
|
||||
|
||||
afterAll(async () => {
|
||||
// @ts-ignore
|
||||
await WidgetLayoutStore.instance.onNotReady();
|
||||
// @ts-ignore
|
||||
await RightPanelStore.instance.onNotReady();
|
||||
jest.restoreAllMocks();
|
||||
});
|
||||
|
||||
describe("for a pinned widget", () => {
|
||||
let renderResult: RenderResult;
|
||||
let moveToContainerSpy: jest.SpyInstance<void, [room: Room, widget: IWidget, toContainer: Container]>;
|
||||
|
||||
beforeEach(async () => {
|
||||
renderResult = render(
|
||||
moveToContainerSpy = jest.spyOn(WidgetLayoutStore.instance, "moveToContainer");
|
||||
});
|
||||
|
||||
it("should render", async () => {
|
||||
const renderResult = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
|
||||
moveToContainerSpy = jest.spyOn(WidgetLayoutStore.instance, "moveToContainer");
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
});
|
||||
|
||||
it("should render", () => {
|
||||
const { asFragment } = renderResult;
|
||||
|
||||
expect(asFragment()).toMatchSnapshot(); // Take a snapshot of the pinned widget
|
||||
});
|
||||
|
||||
it("should not display the »Popout widget« button", () => {
|
||||
it("should not display the »Popout widget« button", async () => {
|
||||
const renderResult = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
expect(renderResult.queryByLabelText("Popout widget")).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("clicking 'minimise' should send the widget to the right", async () => {
|
||||
const renderResult = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
await userEvent.click(renderResult.getByLabelText("Minimise"));
|
||||
expect(moveToContainerSpy).toHaveBeenCalledWith(r1, app1, Container.Right);
|
||||
});
|
||||
|
||||
it("clicking 'maximise' should send the widget to the center", async () => {
|
||||
const renderResult = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
await userEvent.click(renderResult.getByLabelText("Maximise"));
|
||||
expect(moveToContainerSpy).toHaveBeenCalledWith(r1, app1, Container.Center);
|
||||
});
|
||||
|
||||
it("should render permission request", () => {
|
||||
it("should render permission request", async () => {
|
||||
jest.spyOn(ModuleRunner.instance, "invoke").mockImplementation((lifecycleEvent, opts, widgetInfo) => {
|
||||
if (lifecycleEvent === WidgetLifecycle.PreLoadRequest && (widgetInfo as WidgetInfo).id === app1.id) {
|
||||
(opts as ApprovalOpts).approved = false;
|
||||
@ -378,21 +398,17 @@ describe("AppTile", () => {
|
||||
});
|
||||
|
||||
// userId and creatorUserId are different
|
||||
const renderResult = render(
|
||||
const { container, asFragment, queryByRole } = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} userId="@user1" creatorUserId="@userAnother" />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
|
||||
const { container, asFragment } = renderResult;
|
||||
|
||||
expect(container.querySelector(".mx_Spinner")).toBeFalsy();
|
||||
expect(queryByRole("button", { name: "Continue" })).toBeInTheDocument();
|
||||
expect(asFragment()).toMatchSnapshot();
|
||||
|
||||
expect(renderResult.queryByRole("button", { name: "Continue" })).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("should not display 'Continue' button on permission load", () => {
|
||||
it("should not display 'Continue' button on permission load", async () => {
|
||||
jest.spyOn(ModuleRunner.instance, "invoke").mockImplementation((lifecycleEvent, opts, widgetInfo) => {
|
||||
if (lifecycleEvent === WidgetLifecycle.PreLoadRequest && (widgetInfo as WidgetInfo).id === app1.id) {
|
||||
(opts as ApprovalOpts).approved = true;
|
||||
@ -405,6 +421,7 @@ describe("AppTile", () => {
|
||||
<AppTile key={app1.id} app={app1} room={r1} userId="@user1" creatorUserId="@userAnother" />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
|
||||
expect(renderResult.queryByRole("button", { name: "Continue" })).not.toBeInTheDocument();
|
||||
});
|
||||
@ -418,7 +435,17 @@ describe("AppTile", () => {
|
||||
);
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
jest.spyOn(WidgetLayoutStore.instance, "isInContainer").mockRestore();
|
||||
});
|
||||
|
||||
it("clicking 'un-maximise' should send the widget to the top", async () => {
|
||||
const renderResult = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
await userEvent.click(renderResult.getByLabelText("Un-maximise"));
|
||||
expect(moveToContainerSpy).toHaveBeenCalledWith(r1, app1, Container.Top);
|
||||
});
|
||||
@ -440,36 +467,28 @@ describe("AppTile", () => {
|
||||
|
||||
const mockWidget = new ElementWidget(app1);
|
||||
WidgetMessagingStore.instance.storeMessaging(mockWidget, r1.roomId, messaging);
|
||||
});
|
||||
|
||||
renderResult = render(
|
||||
it("should display the »Popout widget« button", async () => {
|
||||
const renderResult = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} room={r1} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
});
|
||||
|
||||
it("should display the »Popout widget« button", () => {
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
expect(renderResult.getByLabelText("Popout widget")).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe("for a persistent app", () => {
|
||||
let renderResult: RenderResult;
|
||||
|
||||
beforeEach(async () => {
|
||||
renderResult = render(
|
||||
it("should render", async () => {
|
||||
const { asFragment, queryByRole } = render(
|
||||
<MatrixClientContext.Provider value={cli}>
|
||||
<AppTile key={app1.id} app={app1} fullWidth={true} room={r1} miniMode={true} showMenubar={false} />
|
||||
<AppTile key={app1.id} app={app1} room={r1} fullWidth={true} miniMode={true} showMenubar={false} />
|
||||
</MatrixClientContext.Provider>,
|
||||
);
|
||||
|
||||
await waitForElementToBeRemoved(() => renderResult.queryByRole("progressbar"));
|
||||
});
|
||||
|
||||
it("should render", async () => {
|
||||
const { asFragment } = renderResult;
|
||||
|
||||
await waitForElementToBeRemoved(() => queryByRole("progressbar"));
|
||||
expect(asFragment()).toMatchSnapshot();
|
||||
});
|
||||
});
|
||||
|
||||
@ -131,7 +131,7 @@ exports[`AppTile for a pinned widget should render 1`] = `
|
||||
class="mx_AppTileMenuBar_widgets"
|
||||
>
|
||||
<div
|
||||
aria-label="Un-maximise"
|
||||
aria-label="Maximise"
|
||||
class="mx_AccessibleButton mx_AppTileMenuBar_widgets_button"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
@ -145,7 +145,7 @@ exports[`AppTile for a pinned widget should render 1`] = `
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
>
|
||||
<path
|
||||
d="M12 11.034a1 1 0 0 0 .29.702l.005.005c.18.18.43.29.705.29h8a1 1 0 0 0 0-2h-5.586L22 3.445a1 1 0 0 0-1.414-1.414L14 8.617V3.031a1 1 0 1 0-2 0zm0 1.963a1 1 0 0 0-.29-.702l-.005-.004A1 1 0 0 0 11 12H3a1 1 0 1 0 0 2h5.586L2 20.586A1 1 0 1 0 3.414 22L10 15.414V21a1 1 0 0 0 2 0z"
|
||||
d="M21 3.997a1 1 0 0 0-.29-.702l-.005-.004A1 1 0 0 0 20 3h-8a1 1 0 1 0 0 2h5.586L5 17.586V12a1 1 0 1 0-2 0v8.003a1 1 0 0 0 .29.702l.005.004c.18.18.43.291.705.291h8a1 1 0 1 0 0-2H6.414L19 6.414V12a1 1 0 1 0 2 0z"
|
||||
/>
|
||||
</svg>
|
||||
</div>
|
||||
@ -244,7 +244,7 @@ exports[`AppTile for a pinned widget should render permission request 1`] = `
|
||||
class="mx_AppTileMenuBar_widgets"
|
||||
>
|
||||
<div
|
||||
aria-label="Un-maximise"
|
||||
aria-label="Maximise"
|
||||
class="mx_AccessibleButton mx_AppTileMenuBar_widgets_button"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
@ -258,7 +258,7 @@ exports[`AppTile for a pinned widget should render permission request 1`] = `
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
>
|
||||
<path
|
||||
d="M12 11.034a1 1 0 0 0 .29.702l.005.005c.18.18.43.29.705.29h8a1 1 0 0 0 0-2h-5.586L22 3.445a1 1 0 0 0-1.414-1.414L14 8.617V3.031a1 1 0 1 0-2 0zm0 1.963a1 1 0 0 0-.29-.702l-.005-.004A1 1 0 0 0 11 12H3a1 1 0 1 0 0 2h5.586L2 20.586A1 1 0 1 0 3.414 22L10 15.414V21a1 1 0 0 0 2 0z"
|
||||
d="M21 3.997a1 1 0 0 0-.29-.702l-.005-.004A1 1 0 0 0 20 3h-8a1 1 0 1 0 0 2h5.586L5 17.586V12a1 1 0 1 0-2 0v8.003a1 1 0 0 0 .29.702l.005.004c.18.18.43.291.705.291h8a1 1 0 1 0 0-2H6.414L19 6.414V12a1 1 0 1 0 2 0z"
|
||||
/>
|
||||
</svg>
|
||||
</div>
|
||||
@ -340,8 +340,8 @@ exports[`AppTile for a pinned widget should render permission request 1`] = `
|
||||
<span>
|
||||
Using this widget may share data
|
||||
<div
|
||||
aria-describedby="_r_2n_"
|
||||
aria-labelledby="_r_2m_"
|
||||
aria-describedby="_r_2f_"
|
||||
aria-labelledby="_r_2e_"
|
||||
class="mx_TextWithTooltip_target mx_TextWithTooltip_target--helpIcon"
|
||||
>
|
||||
<svg
|
||||
|
||||
Loading…
Reference in New Issue
Block a user