Remove old code
This commit is contained in:
@@ -1,452 +0,0 @@
|
||||
/*
|
||||
Copyright 2024 New Vector Ltd.
|
||||
Copyright 2022 The Matrix.org Foundation C.I.C.
|
||||
Copyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>
|
||||
|
||||
SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only
|
||||
Please see LICENSE files in the repository root for full details.
|
||||
*/
|
||||
|
||||
import React from "react";
|
||||
import {
|
||||
act,
|
||||
fireEvent,
|
||||
render,
|
||||
RenderResult,
|
||||
screen,
|
||||
waitFor,
|
||||
waitForElementToBeRemoved,
|
||||
cleanup,
|
||||
} from "jest-matrix-react";
|
||||
import { Room, MatrixClient, RoomState, RoomMember, User, MatrixEvent } from "matrix-js-sdk/src/matrix";
|
||||
import { KnownMembership } from "matrix-js-sdk/src/types";
|
||||
import { mocked, MockedObject } from "jest-mock";
|
||||
|
||||
import { MatrixClientPeg } from "../../../../../src/MatrixClientPeg";
|
||||
import * as TestUtils from "../../../../test-utils";
|
||||
import MemberList from "../../../../../src/components/views/rooms/MemberList";
|
||||
import { SDKContext } from "../../../../../src/contexts/SDKContext";
|
||||
import { TestSdkContext } from "../../../TestSdkContext";
|
||||
import {
|
||||
filterConsole,
|
||||
flushPromises,
|
||||
getMockClientWithEventEmitter,
|
||||
mockClientMethodsRooms,
|
||||
mockClientMethodsUser,
|
||||
} from "../../../../test-utils";
|
||||
import { shouldShowComponent } from "../../../../../src/customisations/helpers/UIComponents";
|
||||
import defaultDispatcher from "../../../../../src/dispatcher/dispatcher";
|
||||
|
||||
jest.mock("../../../../../src/customisations/helpers/UIComponents", () => ({
|
||||
shouldShowComponent: jest.fn(),
|
||||
}));
|
||||
|
||||
function generateRoomId() {
|
||||
return "!" + Math.random().toString().slice(2, 10) + ":domain";
|
||||
}
|
||||
|
||||
describe("MemberList", () => {
|
||||
filterConsole(
|
||||
"Age for event was not available, using `now - origin_server_ts` as a fallback. If the device clock is not correct issues might occur.",
|
||||
);
|
||||
function createRoom(opts = {}) {
|
||||
const room = new Room(generateRoomId(), client, client.getUserId()!);
|
||||
if (opts) {
|
||||
Object.assign(room, opts);
|
||||
}
|
||||
return room;
|
||||
}
|
||||
|
||||
let client: MatrixClient;
|
||||
let root: RenderResult;
|
||||
let memberListRoom: Room;
|
||||
let memberList: MemberList;
|
||||
|
||||
let adminUsers: RoomMember[] = [];
|
||||
let moderatorUsers: RoomMember[] = [];
|
||||
let defaultUsers: RoomMember[] = [];
|
||||
|
||||
function memberString(member: RoomMember): string {
|
||||
if (!member) {
|
||||
return "(null)";
|
||||
} else {
|
||||
const u = member.user;
|
||||
return (
|
||||
"(" +
|
||||
member.name +
|
||||
", " +
|
||||
member.powerLevel +
|
||||
", " +
|
||||
(u ? u.lastActiveAgo : "<null>") +
|
||||
", " +
|
||||
(u ? u.getLastActiveTs() : "<null>") +
|
||||
", " +
|
||||
(u ? u.currentlyActive : "<null>") +
|
||||
", " +
|
||||
(u ? u.presence : "<null>") +
|
||||
")"
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
function expectOrderedByPresenceAndPowerLevel(memberTiles: NodeListOf<Element>, isPresenceEnabled: boolean) {
|
||||
let prevMember: RoomMember | undefined;
|
||||
for (const tile of memberTiles) {
|
||||
const memberA = prevMember;
|
||||
const memberB = memberListRoom.currentState.members[tile.getAttribute("aria-label")!.split(" ")[0]];
|
||||
prevMember = memberB; // just in case an expect fails, set this early
|
||||
if (!memberA) {
|
||||
continue;
|
||||
}
|
||||
|
||||
console.log("COMPARING A VS B:", memberString(memberA), memberString(memberB));
|
||||
|
||||
const userA = memberA.user!;
|
||||
const userB = memberB.user!;
|
||||
|
||||
let groupChange = false;
|
||||
|
||||
if (isPresenceEnabled) {
|
||||
const convertPresence = (p: string) => (p === "unavailable" ? "online" : p);
|
||||
const presenceIndex = (p: string) => {
|
||||
const order = ["active", "online", "offline"];
|
||||
const idx = order.indexOf(convertPresence(p));
|
||||
return idx === -1 ? order.length : idx; // unknown states at the end
|
||||
};
|
||||
|
||||
const idxA = presenceIndex(userA.currentlyActive ? "active" : userA.presence);
|
||||
const idxB = presenceIndex(userB.currentlyActive ? "active" : userB.presence);
|
||||
console.log("Comparing presence groups...");
|
||||
expect(idxB).toBeGreaterThanOrEqual(idxA);
|
||||
groupChange = idxA !== idxB;
|
||||
} else {
|
||||
console.log("Skipped presence groups");
|
||||
}
|
||||
|
||||
if (!groupChange) {
|
||||
console.log("Comparing power levels...");
|
||||
expect(memberA.powerLevel).toBeGreaterThanOrEqual(memberB.powerLevel);
|
||||
groupChange = memberA.powerLevel !== memberB.powerLevel;
|
||||
} else {
|
||||
console.log("Skipping power level check due to group change");
|
||||
}
|
||||
|
||||
if (!groupChange) {
|
||||
if (isPresenceEnabled) {
|
||||
console.log("Comparing last active timestamp...");
|
||||
expect(userB.getLastActiveTs()).toBeLessThanOrEqual(userA.getLastActiveTs());
|
||||
groupChange = userA.getLastActiveTs() !== userB.getLastActiveTs();
|
||||
} else {
|
||||
console.log("Skipping last active timestamp");
|
||||
}
|
||||
} else {
|
||||
console.log("Skipping last active timestamp check due to group change");
|
||||
}
|
||||
|
||||
if (!groupChange) {
|
||||
const nameA = memberA.name[0] === "@" ? memberA.name.slice(1) : memberA.name;
|
||||
const nameB = memberB.name[0] === "@" ? memberB.name.slice(1) : memberB.name;
|
||||
const collator = new Intl.Collator();
|
||||
const nameCompare = collator.compare(nameB, nameA);
|
||||
console.log("Comparing name");
|
||||
expect(nameCompare).toBeGreaterThanOrEqual(0);
|
||||
} else {
|
||||
console.log("Skipping name check due to group change");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function renderMemberList(enablePresence: boolean): void {
|
||||
TestUtils.stubClient();
|
||||
client = MatrixClientPeg.safeGet();
|
||||
client.hasLazyLoadMembersEnabled = () => false;
|
||||
|
||||
// Make room
|
||||
memberListRoom = createRoom();
|
||||
expect(memberListRoom.roomId).toBeTruthy();
|
||||
|
||||
// Make users
|
||||
adminUsers = [];
|
||||
moderatorUsers = [];
|
||||
defaultUsers = [];
|
||||
const usersPerLevel = 2;
|
||||
for (let i = 0; i < usersPerLevel; i++) {
|
||||
const adminUser = new RoomMember(memberListRoom.roomId, `@admin${i}:localhost`);
|
||||
adminUser.membership = KnownMembership.Join;
|
||||
adminUser.powerLevel = 100;
|
||||
adminUser.user = User.createUser(adminUser.userId, client);
|
||||
adminUser.user.currentlyActive = true;
|
||||
adminUser.user.presence = "online";
|
||||
adminUser.user.lastPresenceTs = 1000;
|
||||
adminUser.user.lastActiveAgo = 10;
|
||||
adminUsers.push(adminUser);
|
||||
|
||||
const moderatorUser = new RoomMember(memberListRoom.roomId, `@moderator${i}:localhost`);
|
||||
moderatorUser.membership = KnownMembership.Join;
|
||||
moderatorUser.powerLevel = 50;
|
||||
moderatorUser.user = User.createUser(moderatorUser.userId, client);
|
||||
moderatorUser.user.currentlyActive = true;
|
||||
moderatorUser.user.presence = "online";
|
||||
moderatorUser.user.lastPresenceTs = 1000;
|
||||
moderatorUser.user.lastActiveAgo = 10;
|
||||
moderatorUsers.push(moderatorUser);
|
||||
|
||||
const defaultUser = new RoomMember(memberListRoom.roomId, `@default${i}:localhost`);
|
||||
defaultUser.membership = KnownMembership.Join;
|
||||
defaultUser.powerLevel = 0;
|
||||
defaultUser.user = User.createUser(defaultUser.userId, client);
|
||||
defaultUser.user.currentlyActive = true;
|
||||
defaultUser.user.presence = "online";
|
||||
defaultUser.user.lastPresenceTs = 1000;
|
||||
defaultUser.user.lastActiveAgo = 10;
|
||||
defaultUsers.push(defaultUser);
|
||||
}
|
||||
|
||||
client.getRoom = (roomId) => {
|
||||
if (roomId === memberListRoom.roomId) return memberListRoom;
|
||||
else return null;
|
||||
};
|
||||
memberListRoom.currentState = {
|
||||
members: {},
|
||||
getMember: jest.fn(),
|
||||
getStateEvents: ((eventType, stateKey) =>
|
||||
stateKey === undefined ? [] : null) as RoomState["getStateEvents"], // ignore 3pid invites
|
||||
} as unknown as RoomState;
|
||||
for (const member of [...adminUsers, ...moderatorUsers, ...defaultUsers]) {
|
||||
memberListRoom.currentState.members[member.userId] = member;
|
||||
}
|
||||
|
||||
const gatherWrappedRef = (r: MemberList) => {
|
||||
memberList = r;
|
||||
};
|
||||
const context = new TestSdkContext();
|
||||
context.client = client;
|
||||
context.memberListStore.isPresenceEnabled = jest.fn().mockReturnValue(enablePresence);
|
||||
root = render(
|
||||
<SDKContext.Provider value={context}>
|
||||
<MemberList
|
||||
searchQuery=""
|
||||
onClose={jest.fn()}
|
||||
onSearchQueryChanged={jest.fn()}
|
||||
roomId={memberListRoom.roomId}
|
||||
ref={gatherWrappedRef}
|
||||
/>
|
||||
</SDKContext.Provider>,
|
||||
);
|
||||
}
|
||||
|
||||
describe.each([false, true])("does order members correctly (presence %s)", (enablePresence) => {
|
||||
beforeEach(function () {
|
||||
renderMemberList(enablePresence);
|
||||
});
|
||||
|
||||
describe("does order members correctly", () => {
|
||||
// Note: even if presence is disabled, we still expect that the presence
|
||||
// tests will pass. All expectOrderedByPresenceAndPowerLevel does is ensure
|
||||
// the order is perceived correctly, regardless of what we did to the members.
|
||||
|
||||
// Each of the 4 tests here is done to prove that the member list can meet
|
||||
// all 4 criteria independently. Together, they should work.
|
||||
|
||||
it("by presence state", async () => {
|
||||
// Intentionally pick users that will confuse the power level sorting
|
||||
const activeUsers = [defaultUsers[0]];
|
||||
const onlineUsers = [adminUsers[0]];
|
||||
const offlineUsers = [...moderatorUsers, ...adminUsers.slice(1), ...defaultUsers.slice(1)];
|
||||
activeUsers.forEach((u) => {
|
||||
u.user!.currentlyActive = true;
|
||||
u.user!.presence = "online";
|
||||
});
|
||||
onlineUsers.forEach((u) => {
|
||||
u.user!.currentlyActive = false;
|
||||
u.user!.presence = "online";
|
||||
});
|
||||
offlineUsers.forEach((u) => {
|
||||
u.user!.currentlyActive = false;
|
||||
u.user!.presence = "offline";
|
||||
});
|
||||
|
||||
// Bypass all the event listeners and skip to the good part
|
||||
await act(() => memberList.updateListNow(true));
|
||||
|
||||
const tiles = root.container.querySelectorAll(".mx_EntityTile");
|
||||
expectOrderedByPresenceAndPowerLevel(tiles, enablePresence);
|
||||
});
|
||||
|
||||
it("by power level", async () => {
|
||||
// We already have admin, moderator, and default users so leave them alone
|
||||
|
||||
// Bypass all the event listeners and skip to the good part
|
||||
await act(() => memberList.updateListNow(true));
|
||||
|
||||
const tiles = root.container.querySelectorAll(".mx_EntityTile");
|
||||
expectOrderedByPresenceAndPowerLevel(tiles, enablePresence);
|
||||
});
|
||||
|
||||
it("by last active timestamp", async () => {
|
||||
// Intentionally pick users that will confuse the power level sorting
|
||||
// lastActiveAgoTs == lastPresenceTs - lastActiveAgo
|
||||
const activeUsers = [defaultUsers[0]];
|
||||
const semiActiveUsers = [adminUsers[0]];
|
||||
const inactiveUsers = [...moderatorUsers, ...adminUsers.slice(1), ...defaultUsers.slice(1)];
|
||||
activeUsers.forEach((u) => {
|
||||
u.powerLevel = 100; // set everyone to the same PL to avoid running that check
|
||||
u.user!.lastPresenceTs = 1000;
|
||||
u.user!.lastActiveAgo = 0;
|
||||
});
|
||||
semiActiveUsers.forEach((u) => {
|
||||
u.powerLevel = 100;
|
||||
u.user!.lastPresenceTs = 1000;
|
||||
u.user!.lastActiveAgo = 50;
|
||||
});
|
||||
inactiveUsers.forEach((u) => {
|
||||
u.powerLevel = 100;
|
||||
u.user!.lastPresenceTs = 1000;
|
||||
u.user!.lastActiveAgo = 100;
|
||||
});
|
||||
|
||||
// Bypass all the event listeners and skip to the good part
|
||||
await act(() => memberList.updateListNow(true));
|
||||
|
||||
const tiles = root.container.querySelectorAll(".mx_EntityTile");
|
||||
expectOrderedByPresenceAndPowerLevel(tiles, enablePresence);
|
||||
});
|
||||
|
||||
it("by name", async () => {
|
||||
// Intentionally put everyone on the same level to force a name comparison
|
||||
const allUsers = [...adminUsers, ...moderatorUsers, ...defaultUsers];
|
||||
allUsers.forEach((u) => {
|
||||
u.user!.currentlyActive = true;
|
||||
u.user!.presence = "online";
|
||||
u.user!.lastPresenceTs = 1000;
|
||||
u.user!.lastActiveAgo = 0;
|
||||
u.powerLevel = 100;
|
||||
});
|
||||
|
||||
// Bypass all the event listeners and skip to the good part
|
||||
await act(() => memberList.updateListNow(true));
|
||||
|
||||
const tiles = root.container.querySelectorAll(".mx_EntityTile");
|
||||
expectOrderedByPresenceAndPowerLevel(tiles, enablePresence);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe("memberlist is rendered correctly", () => {
|
||||
beforeEach(function () {
|
||||
renderMemberList(true);
|
||||
});
|
||||
|
||||
it("memberlist is re-rendered on unreachable presence event", async () => {
|
||||
defaultUsers[0].user?.setPresenceEvent(
|
||||
new MatrixEvent({
|
||||
type: "m.presence",
|
||||
sender: defaultUsers[0].userId,
|
||||
content: {
|
||||
presence: "io.element.unreachable",
|
||||
currently_active: false,
|
||||
},
|
||||
}),
|
||||
);
|
||||
expect(await screen.findByText(/User's server unreachable/)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
describe("Invite button", () => {
|
||||
const roomId = "!room:server.org";
|
||||
let client!: MockedObject<MatrixClient>;
|
||||
let room!: Room;
|
||||
|
||||
beforeEach(function () {
|
||||
mocked(shouldShowComponent).mockReturnValue(true);
|
||||
client = getMockClientWithEventEmitter({
|
||||
...mockClientMethodsUser(),
|
||||
...mockClientMethodsRooms(),
|
||||
getRoom: jest.fn(),
|
||||
hasLazyLoadMembersEnabled: jest.fn(),
|
||||
});
|
||||
room = new Room(roomId, client, client.getSafeUserId());
|
||||
client.getRoom.mockReturnValue(room);
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
jest.restoreAllMocks();
|
||||
cleanup();
|
||||
});
|
||||
|
||||
const renderComponent = () => {
|
||||
const context = new TestSdkContext();
|
||||
context.client = client;
|
||||
return render(
|
||||
<SDKContext.Provider value={context}>
|
||||
<MemberList
|
||||
searchQuery=""
|
||||
onClose={jest.fn()}
|
||||
onSearchQueryChanged={jest.fn()}
|
||||
roomId={room.roomId}
|
||||
/>
|
||||
</SDKContext.Provider>,
|
||||
);
|
||||
};
|
||||
|
||||
it("does not render invite button when current user is not a member", async () => {
|
||||
renderComponent();
|
||||
await flushPromises();
|
||||
|
||||
expect(screen.queryByText("Invite to this room")).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("does not render invite button UI customisation hides invites", async () => {
|
||||
mocked(shouldShowComponent).mockReturnValue(false);
|
||||
renderComponent();
|
||||
await flushPromises();
|
||||
|
||||
expect(screen.queryByText("Invite to this room")).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("renders disabled invite button when current user is a member but does not have rights to invite", async () => {
|
||||
jest.spyOn(room, "getMyMembership").mockReturnValue(KnownMembership.Join);
|
||||
jest.spyOn(room, "canInvite").mockReturnValue(false);
|
||||
|
||||
const { findByLabelText } = renderComponent();
|
||||
|
||||
// button rendered but disabled
|
||||
await expect(findByLabelText("You do not have permission to invite users")).resolves.toHaveAttribute(
|
||||
"aria-disabled",
|
||||
"true",
|
||||
);
|
||||
});
|
||||
|
||||
it("renders enabled invite button when current user is a member and has rights to invite", async () => {
|
||||
jest.spyOn(room, "getMyMembership").mockReturnValue(KnownMembership.Join);
|
||||
jest.spyOn(room, "canInvite").mockReturnValue(true);
|
||||
|
||||
const { findByText } = renderComponent();
|
||||
|
||||
await expect(findByText("Invite to this room")).resolves.not.toBeDisabled();
|
||||
});
|
||||
|
||||
it("opens room inviter on button click", async () => {
|
||||
jest.spyOn(defaultDispatcher, "dispatch");
|
||||
jest.spyOn(room, "getMyMembership").mockReturnValue(KnownMembership.Join);
|
||||
jest.spyOn(room, "canInvite").mockReturnValue(true);
|
||||
|
||||
const { getByRole } = renderComponent();
|
||||
await waitForElementToBeRemoved(() => screen.queryAllByRole("progressbar"));
|
||||
|
||||
await waitFor(() =>
|
||||
expect(getByRole("button", { name: "Invite to this room" })).not.toHaveAttribute(
|
||||
"aria-disabled",
|
||||
"true",
|
||||
),
|
||||
);
|
||||
|
||||
fireEvent.click(getByRole("button", { name: "Invite to this room" }));
|
||||
|
||||
expect(defaultDispatcher.dispatch).toHaveBeenCalledWith({
|
||||
action: "view_invite",
|
||||
roomId,
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1,73 +0,0 @@
|
||||
/*
|
||||
* Copyright 2024 New Vector Ltd.
|
||||
* Copyright 2023 The Matrix.org Foundation C.I.C.
|
||||
*
|
||||
* SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only
|
||||
* Please see LICENSE files in the repository root for full details.
|
||||
*/
|
||||
|
||||
import React from "react";
|
||||
import { render, screen, waitFor } from "jest-matrix-react";
|
||||
import { MatrixClient, RoomMember, Device } from "matrix-js-sdk/src/matrix";
|
||||
import { UserVerificationStatus, DeviceVerificationStatus } from "matrix-js-sdk/src/crypto-api";
|
||||
import { mocked } from "jest-mock";
|
||||
import userEvent from "@testing-library/user-event";
|
||||
|
||||
import * as TestUtils from "../../../../test-utils";
|
||||
import MemberTile from "../../../../../src/components/views/rooms/MemberTile";
|
||||
|
||||
describe("MemberTile", () => {
|
||||
let matrixClient: MatrixClient;
|
||||
let member: RoomMember;
|
||||
|
||||
beforeEach(() => {
|
||||
matrixClient = TestUtils.stubClient();
|
||||
mocked(matrixClient.isRoomEncrypted).mockReturnValue(true);
|
||||
member = new RoomMember("roomId", matrixClient.getUserId()!);
|
||||
});
|
||||
|
||||
it("should not display an E2EIcon when the e2E status = normal", () => {
|
||||
const { container } = render(<MemberTile member={member} />);
|
||||
|
||||
expect(container).toMatchSnapshot();
|
||||
});
|
||||
|
||||
it("should display an warning E2EIcon when the e2E status = Warning", async () => {
|
||||
mocked(matrixClient.getCrypto()!.getUserVerificationStatus).mockResolvedValue({
|
||||
isCrossSigningVerified: jest.fn().mockReturnValue(false),
|
||||
wasCrossSigningVerified: jest.fn().mockReturnValue(true),
|
||||
} as unknown as UserVerificationStatus);
|
||||
|
||||
const { container } = render(<MemberTile member={member} />);
|
||||
|
||||
expect(container).toMatchSnapshot();
|
||||
await waitFor(async () => {
|
||||
await userEvent.hover(container.querySelector(".mx_E2EIcon")!);
|
||||
expect(screen.getByText("This user has not verified all of their sessions.")).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
it("should display an verified E2EIcon when the e2E status = Verified", async () => {
|
||||
// Mock all the required crypto methods
|
||||
const deviceMap = new Map<string, Map<string, Device>>();
|
||||
deviceMap.set(member.userId, new Map([["deviceId", {} as Device]]));
|
||||
// Return a DeviceMap = Map<string, Map<string, Device>>
|
||||
mocked(matrixClient.getCrypto()!.getUserDeviceInfo).mockResolvedValue(deviceMap);
|
||||
mocked(matrixClient.getCrypto()!.getUserVerificationStatus).mockResolvedValue({
|
||||
isCrossSigningVerified: jest.fn().mockReturnValue(true),
|
||||
} as unknown as UserVerificationStatus);
|
||||
mocked(matrixClient.getCrypto()!.getDeviceVerificationStatus).mockResolvedValue({
|
||||
crossSigningVerified: true,
|
||||
} as DeviceVerificationStatus);
|
||||
|
||||
const { container } = render(<MemberTile member={member} />);
|
||||
|
||||
expect(container).toMatchSnapshot();
|
||||
await waitFor(async () => {
|
||||
await userEvent.hover(container.querySelector(".mx_E2EIcon")!);
|
||||
expect(
|
||||
screen.getByText("You have verified this user. This user has verified all of their sessions."),
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1,160 +0,0 @@
|
||||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||
|
||||
exports[`MemberTile should display an verified E2EIcon when the e2E status = Verified 1`] = `
|
||||
<div>
|
||||
<div>
|
||||
<div
|
||||
aria-label="@userId:matrix.org (power 0)"
|
||||
class="mx_AccessibleButton mx_EntityTile mx_EntityTile_offline_neveractive"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
>
|
||||
<div
|
||||
class="mx_EntityTile_avatar"
|
||||
>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
class="_avatar_mcap2_17 mx_BaseAvatar _avatar-imageless_mcap2_61"
|
||||
data-color="2"
|
||||
data-testid="avatar-img"
|
||||
data-type="round"
|
||||
role="presentation"
|
||||
style="--cpd-avatar-size: 36px;"
|
||||
title="@userId:matrix.org"
|
||||
>
|
||||
u
|
||||
</span>
|
||||
</div>
|
||||
<div
|
||||
class="mx_EntityTile_details"
|
||||
>
|
||||
<div
|
||||
class="mx_EntityTile_name"
|
||||
>
|
||||
<div
|
||||
class="mx_DisambiguatedProfile"
|
||||
>
|
||||
<span
|
||||
class=""
|
||||
dir="auto"
|
||||
>
|
||||
@userId:matrix.org
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="mx_PresenceLabel"
|
||||
>
|
||||
Offline
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
||||
exports[`MemberTile should display an warning E2EIcon when the e2E status = Warning 1`] = `
|
||||
<div>
|
||||
<div>
|
||||
<div
|
||||
aria-label="@userId:matrix.org (power 0)"
|
||||
class="mx_AccessibleButton mx_EntityTile mx_EntityTile_offline_neveractive"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
>
|
||||
<div
|
||||
class="mx_EntityTile_avatar"
|
||||
>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
class="_avatar_mcap2_17 mx_BaseAvatar _avatar-imageless_mcap2_61"
|
||||
data-color="2"
|
||||
data-testid="avatar-img"
|
||||
data-type="round"
|
||||
role="presentation"
|
||||
style="--cpd-avatar-size: 36px;"
|
||||
title="@userId:matrix.org"
|
||||
>
|
||||
u
|
||||
</span>
|
||||
</div>
|
||||
<div
|
||||
class="mx_EntityTile_details"
|
||||
>
|
||||
<div
|
||||
class="mx_EntityTile_name"
|
||||
>
|
||||
<div
|
||||
class="mx_DisambiguatedProfile"
|
||||
>
|
||||
<span
|
||||
class=""
|
||||
dir="auto"
|
||||
>
|
||||
@userId:matrix.org
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="mx_PresenceLabel"
|
||||
>
|
||||
Offline
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
||||
exports[`MemberTile should not display an E2EIcon when the e2E status = normal 1`] = `
|
||||
<div>
|
||||
<div>
|
||||
<div
|
||||
aria-label="@userId:matrix.org (power 0)"
|
||||
class="mx_AccessibleButton mx_EntityTile mx_EntityTile_offline_neveractive"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
>
|
||||
<div
|
||||
class="mx_EntityTile_avatar"
|
||||
>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
class="_avatar_mcap2_17 mx_BaseAvatar _avatar-imageless_mcap2_61"
|
||||
data-color="2"
|
||||
data-testid="avatar-img"
|
||||
data-type="round"
|
||||
role="presentation"
|
||||
style="--cpd-avatar-size: 36px;"
|
||||
title="@userId:matrix.org"
|
||||
>
|
||||
u
|
||||
</span>
|
||||
</div>
|
||||
<div
|
||||
class="mx_EntityTile_details"
|
||||
>
|
||||
<div
|
||||
class="mx_EntityTile_name"
|
||||
>
|
||||
<div
|
||||
class="mx_DisambiguatedProfile"
|
||||
>
|
||||
<span
|
||||
class=""
|
||||
dir="auto"
|
||||
>
|
||||
@userId:matrix.org
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="mx_PresenceLabel"
|
||||
>
|
||||
Offline
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
Reference in New Issue
Block a user