Skip to content
This repository has been archived by the owner on Sep 11, 2024. It is now read-only.

Commit

Permalink
Update sliding-sync.spec.ts - use Cypress Testing Library (#10618)
Browse files Browse the repository at this point in the history
* Update sliding-sync.spec.ts - use Cypress Testing Library

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Use findByRole() - group, treeitem

The elements with ARIA "treeitem" role resides in ones with ARIA "group" role such as Favourites, People, and Invites. The elements with the "treeitem" role correspond to rooms on the room list.

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Use the library more - 'should render the Rooms list in reverse chronological order by default and allowing sorting A-Z'

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Use cy.findAllByRole("treeitem")

Note the Test room is excluded from being counted thanks to within().

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Rename the rooms to avoid confusion

Since it has been unclear "Join" etc. is a verb or a room name, the room
names are changed as below:

- Join -> Room to Join
- Reject -> Room to Reject (the invite)
- Rescind -> Room to Rescind (the invite)

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Specify ARIA label for the room sublist headers

Have different ARIA labels specified for "mx_RoomSublist" and "mx_RoomSublist_headerContainer" to clarify the structure.

Change the test to check the new ARIA label.

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* lint

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Fix a race condition

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Revert "Specify ARIA label for the room sublist headers"

This reverts commit 193a47d.

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

* Fix realHover() target

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>

---------

Signed-off-by: Suguru Hirahara <luixxiul@users.noreply.github.com>
  • Loading branch information
luixxiul authored Apr 21, 2023
1 parent 7a914e7 commit 05ef1d5
Showing 1 changed file with 122 additions and 65 deletions.
187 changes: 122 additions & 65 deletions cypress/e2e/sliding-sync/sliding-sync.ts
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ describe("Sliding Sync", () => {

// assert order
const checkOrder = (wantOrder: string[]) => {
cy.contains(".mx_RoomSublist", "Rooms")
cy.findByRole("group", { name: "Rooms" })
.find(".mx_RoomTile_title")
.should((elements) => {
expect(
Expand Down Expand Up @@ -102,33 +102,48 @@ describe("Sliding Sync", () => {

it("should render the Rooms list in reverse chronological order by default and allowing sorting A-Z", () => {
// create rooms and check room names are correct
cy.createRoom({ name: "Apple" }).then(() => cy.contains(".mx_RoomSublist", "Apple"));
cy.createRoom({ name: "Pineapple" }).then(() => cy.contains(".mx_RoomSublist", "Pineapple"));
cy.createRoom({ name: "Orange" }).then(() => cy.contains(".mx_RoomSublist", "Orange"));
// check the rooms are in the right order
cy.get(".mx_RoomTile").should("have.length", 4); // due to the Test Room in beforeEach
cy.createRoom({ name: "Apple" }).then(() => cy.findByRole("treeitem", { name: "Apple" }));
cy.createRoom({ name: "Pineapple" }).then(() => cy.findByRole("treeitem", { name: "Pineapple" }));
cy.createRoom({ name: "Orange" }).then(() => cy.findByRole("treeitem", { name: "Orange" }));

cy.get(".mx_RoomSublist_tiles").within(() => {
cy.findAllByRole("treeitem").should("have.length", 4); // due to the Test Room in beforeEach
});

checkOrder(["Orange", "Pineapple", "Apple", "Test Room"]);

cy.contains(".mx_RoomSublist", "Rooms").find(".mx_RoomSublist_menuButton").click({ force: true });
cy.contains("A-Z").click();
cy.get(".mx_StyledRadioButton_checked").should("contain.text", "A-Z");
cy.findByRole("group", { name: "Rooms" }).within(() => {
cy.get(".mx_RoomSublist_headerContainer")
.realHover()
.findByRole("button", { name: "List options" })
.click();
});

// force click as the radio button's size is zero
cy.findByRole("menuitemradio", { name: "A-Z" }).click({ force: true });

// Assert that the radio button is checked
cy.get(".mx_StyledRadioButton_checked").within(() => {
cy.findByText("A-Z").should("exist");
});

checkOrder(["Apple", "Orange", "Pineapple", "Test Room"]);
});

it("should move rooms around as new events arrive", () => {
// create rooms and check room names are correct
cy.createRoom({ name: "Apple" })
.as("roomA")
.then(() => cy.contains(".mx_RoomSublist", "Apple"));
.then(() => cy.findByRole("treeitem", { name: "Apple" }));
cy.createRoom({ name: "Pineapple" })
.as("roomP")
.then(() => cy.contains(".mx_RoomSublist", "Pineapple"));
.then(() => cy.findByRole("treeitem", { name: "Pineapple" }));
cy.createRoom({ name: "Orange" })
.as("roomO")
.then(() => cy.contains(".mx_RoomSublist", "Orange"));
.then(() => cy.findByRole("treeitem", { name: "Orange" }));

// Select the Test Room
cy.contains(".mx_RoomTile", "Test Room").click();
cy.findByRole("treeitem", { name: "Test Room" }).click();

checkOrder(["Orange", "Pineapple", "Apple", "Test Room"]);
bumpRoom("@roomA");
Expand All @@ -145,28 +160,28 @@ describe("Sliding Sync", () => {
// create rooms and check room names are correct
cy.createRoom({ name: "Apple" })
.as("roomA")
.then(() => cy.contains(".mx_RoomSublist", "Apple"));
.then(() => cy.findByRole("treeitem", { name: "Apple" }));
cy.createRoom({ name: "Pineapple" })
.as("roomP")
.then(() => cy.contains(".mx_RoomSublist", "Pineapple"));
.then(() => cy.findByRole("treeitem", { name: "Pineapple" }));
cy.createRoom({ name: "Orange" })
.as("roomO")
.then(() => cy.contains(".mx_RoomSublist", "Orange"));
.then(() => cy.findByRole("treeitem", { name: "Orange" }));

// Given a list of Orange, Pineapple, Apple - if Pineapple is active and a message is sent in Apple, the list should
// turn into Apple, Pineapple, Orange - the index position of Pineapple never changes even though the list should technically
// be Apple, Orange Pineapple - only when you click on a different room do things reshuffle.

// Select the Pineapple room
cy.contains(".mx_RoomTile", "Pineapple").click();
cy.findByRole("treeitem", { name: "Pineapple" }).click();
checkOrder(["Orange", "Pineapple", "Apple", "Test Room"]);

// Move Apple
bumpRoom("@roomA");
checkOrder(["Apple", "Pineapple", "Orange", "Test Room"]);

// Select the Test Room
cy.contains(".mx_RoomTile", "Test Room").click();
cy.findByRole("treeitem", { name: "Test Room" }).click();

// the rooms reshuffle to match reality
checkOrder(["Apple", "Orange", "Pineapple", "Test Room"]);
Expand All @@ -181,28 +196,34 @@ describe("Sliding Sync", () => {
});

// check that there is an unread notification (grey) as 1
cy.contains(".mx_RoomTile", "Test Room").contains(".mx_NotificationBadge_count", "1");
cy.findByRole("treeitem", { name: "Test Room 1 unread message." }).contains(".mx_NotificationBadge_count", "1");
cy.get(".mx_NotificationBadge").should("not.have.class", "mx_NotificationBadge_highlighted");

// send an @mention: highlight count (red) should be 2.
cy.all([cy.get<string>("@roomId"), cy.get<MatrixClient>("@bob")]).then(([roomId, bob]) => {
return bob.sendTextMessage(roomId, "Hello Sloth");
});
cy.contains(".mx_RoomTile", "Test Room").contains(".mx_NotificationBadge_count", "2");
cy.findByRole("treeitem", { name: "Test Room 2 unread messages including mentions." }).contains(
".mx_NotificationBadge_count",
"2",
);
cy.get(".mx_NotificationBadge").should("have.class", "mx_NotificationBadge_highlighted");

// click on the room, the notif counts should disappear
cy.contains(".mx_RoomTile", "Test Room").click();
cy.contains(".mx_RoomTile", "Test Room").should("not.have.class", "mx_NotificationBadge_count");
cy.findByRole("treeitem", { name: "Test Room 2 unread messages including mentions." }).click();
cy.findByRole("treeitem", { name: "Test Room" }).should("not.have.class", "mx_NotificationBadge_count");
});

it("should not show unread indicators", () => {
// TODO: for now. Later we should.
createAndJoinBob();

// disable notifs in this room (TODO: CS API call?)
cy.contains(".mx_RoomTile", "Test Room").find(".mx_RoomTile_notificationsButton").click({ force: true });
cy.contains("Mute room").click();
cy.findByRole("treeitem", { name: "Test Room" })
.realHover()
.findByRole("button", { name: "Notification options" })
.click();
cy.findByRole("menuitemradio", { name: "Mute room" }).click();

// create a new room so we know when the message has been received as it'll re-shuffle the room list
cy.createRoom({
Expand All @@ -216,13 +237,13 @@ describe("Sliding Sync", () => {
// wait for this message to arrive, tell by the room list resorting
checkOrder(["Test Room", "Dummy"]);

cy.contains(".mx_RoomTile", "Test Room").get(".mx_NotificationBadge").should("not.exist");
cy.findByRole("treeitem", { name: "Test Room" }).get(".mx_NotificationBadge").should("not.exist");
});

it("should update user settings promptly", () => {
cy.get(".mx_UserMenu_userAvatar").click();
cy.contains("All settings").click();
cy.contains("Preferences").click();
cy.findByRole("button", { name: "User menu" }).click();
cy.findByRole("menuitem", { name: "All settings" }).click();
cy.findByRole("button", { name: "Preferences" }).click();
cy.contains(".mx_SettingsFlag", "Show timestamps in 12 hour format")
.should("exist")
.find(".mx_ToggleSwitch_on")
Expand Down Expand Up @@ -257,9 +278,9 @@ describe("Sliding Sync", () => {
.then((bob) => {
bobClient = bob;
return Promise.all([
bob.createRoom({ name: "Join" }),
bob.createRoom({ name: "Reject" }),
bob.createRoom({ name: "Rescind" }),
bob.createRoom({ name: "Room to Join" }),
bob.createRoom({ name: "Room to Reject" }),
bob.createRoom({ name: "Room to Rescind" }),
]);
})
.then(([join, reject, rescind]) => {
Expand All @@ -273,41 +294,68 @@ describe("Sliding Sync", () => {
]);
});

// wait for them all to be on the UI
cy.get(".mx_RoomTile").should("have.length", 4); // due to the Test Room in beforeEach
cy.findByRole("group", { name: "Invites" }).within(() => {
// Exclude headerText
cy.get(".mx_RoomSublist_tiles").within(() => {
// Wait for them all to be on the UI
cy.findAllByRole("treeitem").should("have.length", 3);
});
});

// Select the room to join
cy.findByRole("treeitem", { name: "Room to Join" }).click();

cy.contains(".mx_RoomTile", "Join").click();
cy.contains(".mx_AccessibleButton", "Accept").click();
cy.get(".mx_RoomView").within(() => {
// Accept the invite
cy.findByRole("button", { name: "Accept" }).click();
});

checkOrder(["Join", "Test Room"]);
checkOrder(["Room to Join", "Test Room"]);

cy.contains(".mx_RoomTile", "Reject").click();
cy.contains(".mx_RoomView .mx_AccessibleButton", "Reject").click();
// Select the room to reject
cy.findByRole("treeitem", { name: "Room to Reject" }).click();

// wait for the rejected room to disappear
cy.get(".mx_RoomTile").should("have.length", 3);
cy.get(".mx_RoomView").within(() => {
// Reject the invite
cy.findByRole("button", { name: "Reject" }).click();
});

cy.findByRole("group", { name: "Invites" }).within(() => {
// Exclude headerText
cy.get(".mx_RoomSublist_tiles").within(() => {
// Wait for the rejected room to disappear
cy.findAllByRole("treeitem").should("have.length", 2);
});
});

// check the lists are correct
checkOrder(["Join", "Test Room"]);
cy.contains(".mx_RoomSublist", "Invites")
checkOrder(["Room to Join", "Test Room"]);

cy.findByRole("group", { name: "Invites" })
.find(".mx_RoomTile_title")
.should((elements) => {
expect(
_.map(elements, (e) => {
return e.textContent;
}),
"rooms are sorted",
).to.deep.equal(["Rescind"]);
).to.deep.equal(["Room to Rescind"]);
});

// now rescind the invite
cy.get<MatrixClient>("@bob").then((bob) => {
return bob.kick(roomRescind, clientUserId);
});

// wait for the rescind to take effect and check the joined list once more
cy.get(".mx_RoomTile").should("have.length", 2);
checkOrder(["Join", "Test Room"]);
cy.findByRole("group", { name: "Rooms" }).within(() => {
// Exclude headerText
cy.get(".mx_RoomSublist_tiles").within(() => {
// Wait for the rescind to take effect and check the joined list once more
cy.findAllByRole("treeitem").should("have.length", 2);
});
});

checkOrder(["Room to Join", "Test Room"]);
});

it("should show a favourite DM only in the favourite sublist", () => {
Expand All @@ -320,37 +368,41 @@ describe("Sliding Sync", () => {
cy.getClient().then((cli) => cli.setRoomTag(roomId, "m.favourite", { order: 0.5 }));
});

cy.contains('.mx_RoomSublist[aria-label="Favourites"] .mx_RoomTile', "Favourite DM").should("exist");
cy.contains('.mx_RoomSublist[aria-label="People"] .mx_RoomTile', "Favourite DM").should("not.exist");
cy.findByRole("group", { name: "Favourites" }).findByText("Favourite DM").should("exist");
cy.findByRole("group", { name: "People" }).findByText("Favourite DM").should("not.exist");
});

// Regression test for a bug in SS mode, but would be useful to have in non-SS mode too.
// This ensures we are setting RoomViewStore state correctly.
it("should clear the reply to field when swapping rooms", () => {
cy.createRoom({ name: "Other Room" })
.as("roomA")
.then(() => cy.contains(".mx_RoomSublist", "Other Room"));
.then(() => cy.findByRole("treeitem", { name: "Other Room" }));
cy.get<string>("@roomId").then((roomId) => {
return cy.sendEvent(roomId, null, "m.room.message", {
body: "Hello world",
msgtype: "m.text",
});
});
// select the room
cy.contains(".mx_RoomTile", "Test Room").click();
cy.findByRole("treeitem", { name: "Test Room" }).click();
cy.get(".mx_ReplyPreview").should("not.exist");
// click reply-to on the Hello World message
cy.contains(".mx_EventTile", "Hello world")
.find('.mx_AccessibleButton[aria-label="Reply"]')
.click({ force: true });
cy.get(".mx_EventTile_last")
.within(() => {
cy.findByText("Hello world", { timeout: 1000 });
})
.realHover()
.findByRole("button", { name: "Reply" })
.click();
// check it's visible
cy.get(".mx_ReplyPreview").should("exist");
// now click Other Room
cy.contains(".mx_RoomTile", "Other Room").click();
cy.findByRole("treeitem", { name: "Other Room" }).click();
// ensure the reply-to disappears
cy.get(".mx_ReplyPreview").should("not.exist");
// click back
cy.contains(".mx_RoomTile", "Test Room").click();
cy.findByRole("treeitem", { name: "Test Room" }).click();
// ensure the reply-to reappears
cy.get(".mx_ReplyPreview").should("exist");
});
Expand Down Expand Up @@ -378,12 +430,17 @@ describe("Sliding Sync", () => {
});
});
// select the room
cy.contains(".mx_RoomTile", "Test Room").click();
cy.findByRole("treeitem", { name: "Test Room" }).click();
cy.get(".mx_ReplyPreview").should("not.exist");
// click reply-to on the Reply to me message
cy.contains(".mx_EventTile", "Reply to me")
.find('.mx_AccessibleButton[aria-label="Reply"]')
.click({ force: true });
cy.get(".mx_EventTile")
.last()
.within(() => {
cy.findByText("Reply to me");
})
.realHover()
.findByRole("button", { name: "Reply" })
.click();
// check it's visible
cy.get(".mx_ReplyPreview").should("exist");
// now click on the permalink for Permalink me
Expand All @@ -401,15 +458,15 @@ describe("Sliding Sync", () => {
cy.createRoom({ name: "Apple" })
.as("roomA")
.then((roomId) => (roomAId = roomId))
.then(() => cy.contains(".mx_RoomSublist", "Apple"));
.then(() => cy.findByRole("treeitem", { name: "Apple" }));

cy.createRoom({ name: "Pineapple" })
.as("roomP")
.then((roomId) => (roomPId = roomId))
.then(() => cy.contains(".mx_RoomSublist", "Pineapple"));
.then(() => cy.findByRole("treeitem", { name: "Pineapple" }));
cy.createRoom({ name: "Orange" })
.as("roomO")
.then(() => cy.contains(".mx_RoomSublist", "Orange"));
.then(() => cy.findByRole("treeitem", { name: "Orange" }));

// Intercept all calls to /sync
cy.intercept({ method: "POST", url: "**/sync*" }).as("syncRequest");
Expand All @@ -426,7 +483,7 @@ describe("Sliding Sync", () => {
};

// Select the Test Room
cy.contains(".mx_RoomTile", "Apple").click();
cy.findByRole("treeitem", { name: "Apple" }).click();

// and wait for cypress to get the result as alias
cy.wait("@syncRequest").then((interception) => {
Expand All @@ -435,11 +492,11 @@ describe("Sliding Sync", () => {
});

// Switch to another room
cy.contains(".mx_RoomTile", "Pineapple").click();
cy.findByRole("treeitem", { name: "Pineapple" }).click();
cy.wait("@syncRequest").then((interception) => assertUnsubExists(interception, roomPId, roomAId));

// And switch to even another room
cy.contains(".mx_RoomTile", "Apple").click();
cy.findByRole("treeitem", { name: "Apple" }).click();
cy.wait("@syncRequest").then((interception) => assertUnsubExists(interception, roomPId, roomAId));

// TODO: Add tests for encrypted rooms
Expand Down

0 comments on commit 05ef1d5

Please sign in to comment.