mirror of
https://github.com/element-hq/element-web
synced 2024-11-22 09:15:41 +03:00
port BeaconViewDialog unit test to rtl (#10180)
This commit is contained in:
parent
b48d568c69
commit
d141fedff6
3 changed files with 134 additions and 149 deletions
|
@ -158,12 +158,12 @@ const BeaconViewDialog: React.FC<IProps> = ({ initialFocusedBeacon, roomId, matr
|
|||
)}
|
||||
{mapDisplayError && <MapError error={mapDisplayError.message as LocationShareError} isMinimised />}
|
||||
{!centerGeoUri && !mapDisplayError && (
|
||||
<MapFallback data-test-id="beacon-view-dialog-map-fallback" className="mx_BeaconViewDialog_map">
|
||||
<MapFallback data-testid="beacon-view-dialog-map-fallback" className="mx_BeaconViewDialog_map">
|
||||
<span className="mx_BeaconViewDialog_mapFallbackMessage">{_t("No live locations")}</span>
|
||||
<AccessibleButton
|
||||
kind="primary"
|
||||
onClick={onFinished}
|
||||
data-test-id="beacon-view-dialog-fallback-close"
|
||||
data-testid="beacon-view-dialog-fallback-close"
|
||||
>
|
||||
{_t("Close")}
|
||||
</AccessibleButton>
|
||||
|
@ -179,7 +179,7 @@ const BeaconViewDialog: React.FC<IProps> = ({ initialFocusedBeacon, roomId, matr
|
|||
<AccessibleButton
|
||||
kind="primary"
|
||||
onClick={() => setSidebarOpen(true)}
|
||||
data-test-id="beacon-view-dialog-open-sidebar"
|
||||
data-testid="beacon-view-dialog-open-sidebar"
|
||||
className="mx_BeaconViewDialog_viewListButton"
|
||||
>
|
||||
<LiveLocationIcon height={12} />
|
||||
|
|
|
@ -15,17 +15,14 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import React from "react";
|
||||
// eslint-disable-next-line deprecate/import
|
||||
import { mount, ReactWrapper } from "enzyme";
|
||||
import { act } from "react-dom/test-utils";
|
||||
import { fireEvent, render, RenderResult } from "@testing-library/react";
|
||||
import { MatrixClient, MatrixEvent, Room, RoomMember, getBeaconInfoIdentifier } from "matrix-js-sdk/src/matrix";
|
||||
import * as maplibregl from "maplibre-gl";
|
||||
import { mocked } from "jest-mock";
|
||||
|
||||
import BeaconViewDialog from "../../../../src/components/views/beacon/BeaconViewDialog";
|
||||
import {
|
||||
findByAttr,
|
||||
findByTestId,
|
||||
getMockClientWithEventEmitter,
|
||||
makeBeaconEvent,
|
||||
makeBeaconInfoEvent,
|
||||
|
@ -34,8 +31,6 @@ import {
|
|||
} from "../../../test-utils";
|
||||
import { TILE_SERVER_WK_KEY } from "../../../../src/utils/WellKnownUtils";
|
||||
import { OwnBeaconStore } from "../../../../src/stores/OwnBeaconStore";
|
||||
import { BeaconDisplayStatus } from "../../../../src/components/views/beacon/displayStatus";
|
||||
import BeaconListItem from "../../../../src/components/views/beacon/BeaconListItem";
|
||||
|
||||
describe("<BeaconViewDialog />", () => {
|
||||
// 14.03.2022 16:15
|
||||
|
@ -60,6 +55,7 @@ describe("<BeaconViewDialog />", () => {
|
|||
|
||||
const mapOptions = { container: {} as unknown as HTMLElement, style: "" };
|
||||
const mockMap = new maplibregl.Map(mapOptions);
|
||||
const mockMarker = new maplibregl.Marker();
|
||||
|
||||
// make fresh rooms every time
|
||||
// as we update room state
|
||||
|
@ -84,13 +80,11 @@ describe("<BeaconViewDialog />", () => {
|
|||
matrixClient: mockClient as MatrixClient,
|
||||
};
|
||||
|
||||
const getComponent = (props = {}) => mount(<BeaconViewDialog {...defaultProps} {...props} />);
|
||||
const getComponent = (props = {}): RenderResult => render(<BeaconViewDialog {...defaultProps} {...props} />);
|
||||
|
||||
const openSidebar = (component: ReactWrapper) =>
|
||||
act(() => {
|
||||
findByTestId(component, "beacon-view-dialog-open-sidebar").at(0).simulate("click");
|
||||
component.setProps({});
|
||||
});
|
||||
const openSidebar = (getByTestId: RenderResult["getByTestId"]) => {
|
||||
fireEvent.click(getByTestId("beacon-view-dialog-open-sidebar"));
|
||||
};
|
||||
|
||||
beforeEach(() => {
|
||||
jest.spyOn(OwnBeaconStore.instance, "getLiveBeaconIds").mockRestore();
|
||||
|
@ -103,14 +97,14 @@ describe("<BeaconViewDialog />", () => {
|
|||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent();
|
||||
expect(component.find("Map").props()).toEqual(
|
||||
expect.objectContaining({
|
||||
centerGeoUri: "geo:51,41",
|
||||
interactive: true,
|
||||
}),
|
||||
);
|
||||
expect(component.find("SmartMarker").length).toEqual(1);
|
||||
getComponent();
|
||||
// centered on default event
|
||||
expect(mockMap.setCenter).toHaveBeenCalledWith({
|
||||
lon: 41,
|
||||
lat: 51,
|
||||
});
|
||||
// marker added
|
||||
expect(mockMarker.addTo).toHaveBeenCalledWith(mockMap);
|
||||
});
|
||||
|
||||
it("does not render any own beacon status when user is not live sharing", () => {
|
||||
|
@ -118,8 +112,8 @@ describe("<BeaconViewDialog />", () => {
|
|||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent();
|
||||
expect(component.find("DialogOwnBeaconStatus").html()).toBeNull();
|
||||
const { queryByText } = getComponent();
|
||||
expect(queryByText("Live location enabled")).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("renders own beacon status when user is live sharing", () => {
|
||||
|
@ -130,52 +124,47 @@ describe("<BeaconViewDialog />", () => {
|
|||
// mock own beacon store to show default event as alice's live beacon
|
||||
jest.spyOn(OwnBeaconStore.instance, "getLiveBeaconIds").mockReturnValue([beacon.identifier]);
|
||||
jest.spyOn(OwnBeaconStore.instance, "getBeaconById").mockReturnValue(beacon);
|
||||
const component = getComponent();
|
||||
expect(component.find("MemberAvatar").length).toBeTruthy();
|
||||
expect(component.find("OwnBeaconStatus").props()).toEqual({
|
||||
beacon,
|
||||
displayStatus: BeaconDisplayStatus.Active,
|
||||
className: "mx_DialogOwnBeaconStatus_status",
|
||||
});
|
||||
const { container } = getComponent();
|
||||
expect(container.querySelector(".mx_DialogOwnBeaconStatus")).toMatchSnapshot();
|
||||
});
|
||||
|
||||
it("updates markers on changes to beacons", () => {
|
||||
it("updates markers on changes to beacons", async () => {
|
||||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent();
|
||||
expect(component.find("BeaconMarker").length).toEqual(1);
|
||||
const { container } = getComponent();
|
||||
|
||||
// one marker
|
||||
expect(mockMarker.addTo).toHaveBeenCalledTimes(1);
|
||||
expect(container.getElementsByClassName("mx_Marker").length).toEqual(1);
|
||||
|
||||
const anotherBeaconEvent = makeBeaconInfoEvent(bobId, roomId, { isLive: true }, "$bob-room1-1");
|
||||
|
||||
act(() => {
|
||||
// emits RoomStateEvent.BeaconLiveness
|
||||
room.currentState.setStateEvents([anotherBeaconEvent]);
|
||||
const beacon2 = room.currentState.beacons.get(getBeaconInfoIdentifier(anotherBeaconEvent))!;
|
||||
beacon2.addLocations([location1]);
|
||||
});
|
||||
|
||||
component.setProps({});
|
||||
|
||||
// two markers now!
|
||||
expect(component.find("BeaconMarker").length).toEqual(2);
|
||||
expect(container.getElementsByClassName("mx_Marker").length).toEqual(2);
|
||||
});
|
||||
|
||||
it("does not update bounds or center on changing beacons", () => {
|
||||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent();
|
||||
expect(component.find("BeaconMarker").length).toEqual(1);
|
||||
const { container } = getComponent();
|
||||
expect(container.getElementsByClassName("mx_Marker").length).toEqual(1);
|
||||
|
||||
const anotherBeaconEvent = makeBeaconInfoEvent(bobId, roomId, { isLive: true }, "$bob-room1-1");
|
||||
|
||||
act(() => {
|
||||
// emits RoomStateEvent.BeaconLiveness
|
||||
room.currentState.setStateEvents([anotherBeaconEvent]);
|
||||
const beacon2 = room.currentState.beacons.get(getBeaconInfoIdentifier(anotherBeaconEvent))!;
|
||||
beacon2.addLocations([location1]);
|
||||
});
|
||||
|
||||
component.setProps({});
|
||||
|
||||
// two markers now!
|
||||
// called once on init
|
||||
expect(mockMap.setCenter).toHaveBeenCalledTimes(1);
|
||||
expect(mockMap.fitBounds).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
@ -185,14 +174,12 @@ describe("<BeaconViewDialog />", () => {
|
|||
const onFinished = jest.fn();
|
||||
const room = setupRoom([defaultEvent]);
|
||||
room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent));
|
||||
const component = getComponent({ onFinished });
|
||||
const { getByTestId } = getComponent({ onFinished });
|
||||
|
||||
// map placeholder
|
||||
expect(findByTestId(component, "beacon-view-dialog-map-fallback")).toMatchSnapshot();
|
||||
expect(getByTestId("beacon-view-dialog-map-fallback")).toMatchSnapshot();
|
||||
|
||||
act(() => {
|
||||
findByTestId(component, "beacon-view-dialog-fallback-close").at(0).simulate("click");
|
||||
});
|
||||
fireEvent.click(getByTestId("beacon-view-dialog-fallback-close"));
|
||||
|
||||
expect(onFinished).toHaveBeenCalled();
|
||||
});
|
||||
|
@ -202,8 +189,8 @@ describe("<BeaconViewDialog />", () => {
|
|||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent({ onFinished });
|
||||
expect(component.find("BeaconMarker").length).toEqual(1);
|
||||
const { container } = getComponent({ onFinished });
|
||||
expect(container.getElementsByClassName("mx_Marker").length).toEqual(1);
|
||||
|
||||
// this will replace the defaultEvent
|
||||
// leading to no more live beacons
|
||||
|
@ -219,12 +206,10 @@ describe("<BeaconViewDialog />", () => {
|
|||
room.currentState.setStateEvents([anotherBeaconEvent]);
|
||||
});
|
||||
|
||||
component.setProps({});
|
||||
|
||||
// no more avatars
|
||||
expect(component.find("MemberAvatar").length).toBeFalsy();
|
||||
expect(container.getElementsByClassName("mx_Marker").length).toEqual(0);
|
||||
// map still rendered
|
||||
expect(component.find("Map").length).toBeTruthy();
|
||||
expect(container.querySelector("#mx_Map_mx_BeaconViewDialog")).toBeInTheDocument();
|
||||
// map location unchanged
|
||||
expect(mockMap.setCenter).not.toHaveBeenCalled();
|
||||
expect(mockMap.fitBounds).not.toHaveBeenCalled();
|
||||
|
@ -235,31 +220,28 @@ describe("<BeaconViewDialog />", () => {
|
|||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent();
|
||||
const { container, getByTestId } = getComponent();
|
||||
|
||||
openSidebar(component);
|
||||
openSidebar(getByTestId);
|
||||
|
||||
expect(component.find("DialogSidebar").length).toBeTruthy();
|
||||
expect(container.querySelector(".mx_DialogSidebar")).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("closes sidebar on close button click", () => {
|
||||
const room = setupRoom([defaultEvent]);
|
||||
const beacon = room.currentState.beacons.get(getBeaconInfoIdentifier(defaultEvent))!;
|
||||
beacon.addLocations([location1]);
|
||||
const component = getComponent();
|
||||
const { container, getByTestId } = getComponent();
|
||||
|
||||
// open the sidebar
|
||||
openSidebar(component);
|
||||
openSidebar(getByTestId);
|
||||
|
||||
expect(component.find("DialogSidebar").length).toBeTruthy();
|
||||
expect(container.querySelector(".mx_DialogSidebar")).toBeInTheDocument();
|
||||
|
||||
// now close it
|
||||
act(() => {
|
||||
findByAttr("data-testid")(component, "dialog-sidebar-close").at(0).simulate("click");
|
||||
component.setProps({});
|
||||
});
|
||||
fireEvent.click(getByTestId("dialog-sidebar-close"));
|
||||
|
||||
expect(component.find("DialogSidebar").length).toBeFalsy();
|
||||
expect(container.querySelector(".mx_DialogSidebar")).not.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
|
@ -326,16 +308,17 @@ describe("<BeaconViewDialog />", () => {
|
|||
[location1, location2],
|
||||
);
|
||||
|
||||
const component = getComponent({ beacons: [beacon1, beacon2] });
|
||||
const { container, getByTestId } = getComponent({ beacons: [beacon1, beacon2] });
|
||||
|
||||
// reset call counts on map mocks after initial render
|
||||
jest.clearAllMocks();
|
||||
|
||||
openSidebar(component);
|
||||
openSidebar(getByTestId);
|
||||
|
||||
act(() => {
|
||||
const listItems = container.querySelectorAll(".mx_BeaconListItem");
|
||||
// click on the first beacon in the list
|
||||
component.find(BeaconListItem).at(0).simulate("click");
|
||||
fireEvent.click(listItems[0]!);
|
||||
});
|
||||
|
||||
// centered on clicked beacon
|
||||
|
@ -359,16 +342,17 @@ describe("<BeaconViewDialog />", () => {
|
|||
[location1, location2],
|
||||
);
|
||||
|
||||
const component = getComponent({ beacons: [beacon1, beacon2] });
|
||||
const { container, getByTestId } = getComponent({ beacons: [beacon1, beacon2] });
|
||||
|
||||
// reset call counts on map mocks after initial render
|
||||
jest.clearAllMocks();
|
||||
|
||||
openSidebar(component);
|
||||
openSidebar(getByTestId);
|
||||
|
||||
act(() => {
|
||||
// click on the second beacon in the list
|
||||
component.find(BeaconListItem).at(1).simulate("click");
|
||||
const listItems = container.querySelectorAll(".mx_BeaconListItem");
|
||||
fireEvent.click(listItems[1]!);
|
||||
});
|
||||
|
||||
const expectedBounds = new maplibregl.LngLatBounds([22, 33], [22, 33]);
|
||||
|
@ -378,7 +362,8 @@ describe("<BeaconViewDialog />", () => {
|
|||
|
||||
act(() => {
|
||||
// click on the second beacon in the list
|
||||
component.find(BeaconListItem).at(1).simulate("click");
|
||||
const listItems = container.querySelectorAll(".mx_BeaconListItem");
|
||||
fireEvent.click(listItems[1]!);
|
||||
});
|
||||
|
||||
// centered on clicked beacon
|
||||
|
|
|
@ -1,83 +1,83 @@
|
|||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||
|
||||
exports[`<BeaconViewDialog /> renders a fallback when there are no locations 1`] = `
|
||||
[
|
||||
<MapFallback
|
||||
className="mx_BeaconViewDialog_map"
|
||||
data-test-id="beacon-view-dialog-map-fallback"
|
||||
>
|
||||
<div
|
||||
class="mx_MapFallback mx_BeaconViewDialog_map"
|
||||
data-testid="beacon-view-dialog-map-fallback"
|
||||
>
|
||||
<div
|
||||
className="mx_MapFallback mx_BeaconViewDialog_map"
|
||||
data-test-id="beacon-view-dialog-map-fallback"
|
||||
>
|
||||
<div
|
||||
className="mx_MapFallback_bg"
|
||||
class="mx_MapFallback_bg"
|
||||
/>
|
||||
<div
|
||||
className="mx_MapFallback_icon"
|
||||
class="mx_MapFallback_icon"
|
||||
/>
|
||||
<span
|
||||
className="mx_BeaconViewDialog_mapFallbackMessage"
|
||||
class="mx_BeaconViewDialog_mapFallbackMessage"
|
||||
>
|
||||
No live locations
|
||||
</span>
|
||||
<AccessibleButton
|
||||
data-test-id="beacon-view-dialog-fallback-close"
|
||||
element="div"
|
||||
kind="primary"
|
||||
onClick={[MockFunction]}
|
||||
role="button"
|
||||
tabIndex={0}
|
||||
>
|
||||
<div
|
||||
className="mx_AccessibleButton mx_AccessibleButton_hasKind mx_AccessibleButton_kind_primary"
|
||||
data-test-id="beacon-view-dialog-fallback-close"
|
||||
onClick={[MockFunction]}
|
||||
onKeyDown={[Function]}
|
||||
onKeyUp={[Function]}
|
||||
class="mx_AccessibleButton mx_AccessibleButton_hasKind mx_AccessibleButton_kind_primary"
|
||||
data-testid="beacon-view-dialog-fallback-close"
|
||||
role="button"
|
||||
tabIndex={0}
|
||||
tabindex="0"
|
||||
>
|
||||
Close
|
||||
</div>
|
||||
</AccessibleButton>
|
||||
</div>
|
||||
</MapFallback>,
|
||||
<div
|
||||
className="mx_MapFallback mx_BeaconViewDialog_map"
|
||||
data-test-id="beacon-view-dialog-map-fallback"
|
||||
>
|
||||
<div
|
||||
className="mx_MapFallback_bg"
|
||||
/>
|
||||
<div
|
||||
className="mx_MapFallback_icon"
|
||||
/>
|
||||
<span
|
||||
className="mx_BeaconViewDialog_mapFallbackMessage"
|
||||
>
|
||||
No live locations
|
||||
</span>
|
||||
<AccessibleButton
|
||||
data-test-id="beacon-view-dialog-fallback-close"
|
||||
element="div"
|
||||
kind="primary"
|
||||
onClick={[MockFunction]}
|
||||
role="button"
|
||||
tabIndex={0}
|
||||
>
|
||||
<div
|
||||
className="mx_AccessibleButton mx_AccessibleButton_hasKind mx_AccessibleButton_kind_primary"
|
||||
data-test-id="beacon-view-dialog-fallback-close"
|
||||
onClick={[MockFunction]}
|
||||
onKeyDown={[Function]}
|
||||
onKeyUp={[Function]}
|
||||
role="button"
|
||||
tabIndex={0}
|
||||
>
|
||||
Close
|
||||
</div>
|
||||
</AccessibleButton>
|
||||
</div>,
|
||||
]
|
||||
</div>
|
||||
`;
|
||||
|
||||
exports[`<BeaconViewDialog /> renders own beacon status when user is live sharing 1`] = `
|
||||
<div
|
||||
class="mx_DialogOwnBeaconStatus"
|
||||
>
|
||||
<span
|
||||
class="mx_BaseAvatar mx_DialogOwnBeaconStatus_avatar"
|
||||
role="presentation"
|
||||
>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
class="mx_BaseAvatar_initial"
|
||||
style="font-size: 20.8px; width: 32px; line-height: 32px;"
|
||||
>
|
||||
A
|
||||
</span>
|
||||
<img
|
||||
alt=""
|
||||
aria-hidden="true"
|
||||
class="mx_BaseAvatar_image"
|
||||
data-testid="avatar-img"
|
||||
src="data:image/png;base64,00"
|
||||
style="width: 32px; height: 32px;"
|
||||
title="@alice:server"
|
||||
/>
|
||||
</span>
|
||||
<div
|
||||
class="mx_BeaconStatus mx_BeaconStatus_Active mx_DialogOwnBeaconStatus_status"
|
||||
>
|
||||
<div
|
||||
class="mx_BeaconStatus_description"
|
||||
>
|
||||
<span
|
||||
class="mx_BeaconStatus_label"
|
||||
>
|
||||
Live location enabled
|
||||
</span>
|
||||
<span
|
||||
class="mx_LiveTimeRemaining"
|
||||
data-test-id="room-live-share-expiry"
|
||||
>
|
||||
1h left
|
||||
</span>
|
||||
</div>
|
||||
<div
|
||||
class="mx_AccessibleButton mx_OwnBeaconStatus_button mx_OwnBeaconStatus_destructiveButton mx_AccessibleButton_hasKind mx_AccessibleButton_kind_link"
|
||||
data-test-id="beacon-status-stop-beacon"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
>
|
||||
Stop
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
|
Loading…
Reference in a new issue