Skip to content

Commit 2aa79d8

Browse files
test([WPB-19950]): implement regression tests for editing an already sent message (#19748)
1 parent 78b5f0f commit 2aa79d8

File tree

9 files changed

+368
-17
lines changed

9 files changed

+368
-17
lines changed

test/e2e_tests/pageManager/index.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@ import {HistoryExportPage} from './webapp/pages/historyExport.page';
6666
import {HistoryImportPage} from './webapp/pages/historyImport.page';
6767
import {HistoryInfoPage} from './webapp/pages/infoHistory.page';
6868
import {LoginPage} from './webapp/pages/login.page';
69+
import {MessageDetailsPage} from './webapp/pages/messageDetails.page';
6970
import {OptionsPage} from './webapp/pages/options.page';
7071
import {OutgoingConnectionPage} from './webapp/pages/outgoingConnection.page';
7172
import {ParticipantDetails} from './webapp/pages/participantDetails.page';
@@ -176,6 +177,7 @@ export class PageManager {
176177
historyInfo: () => this.getOrCreate('webapp.pages.infoHostory', () => new HistoryInfoPage(this.page)),
177178
historyExport: () => this.getOrCreate('webapp.pages.historyExport', () => new HistoryExportPage(this.page)),
178179
historyImport: () => this.getOrCreate('webapp.pages.historyImport', () => new HistoryImportPage(this.page)),
180+
messageDetails: () => this.getOrCreate('webapp.pages.messageDetails', () => new MessageDetailsPage(this.page)),
179181
participantDetails: () =>
180182
this.getOrCreate('webapp.pages.participantsDetails', () => new ParticipantDetails(this.page)),
181183
requestResetPassword: () =>

test/e2e_tests/pageManager/webapp/pages/conversation.page.ts

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ export class ConversationPage {
5050
readonly conversationInfoButton: Locator;
5151
readonly pingButton: Locator;
5252
readonly messages: Locator;
53+
readonly messageDetails: Locator;
5354
readonly messageItems: Locator;
5455
readonly filesTab: Locator;
5556
readonly isTypingIndicator: Locator;
@@ -95,6 +96,7 @@ export class ConversationPage {
9596
this.messages = page.locator(
9697
`${selectByDataAttribute('item-message')} ${selectByClass('message-body')}:not(:has(p${selectByClass('text-foreground')})):has(${selectByClass('text')})`,
9798
);
99+
this.messageDetails = page.locator('#message-details');
98100
this.filesTab = page.locator('#conversation-tab-files');
99101
this.isTypingIndicator = page.locator(selectByDataAttribute('typing-indicator-title'));
100102
this.itemPendingRequest = page.locator(selectByDataAttribute('item-pending-requests'));
@@ -224,6 +226,42 @@ export class ConversationPage {
224226
return await locator.screenshot();
225227
}
226228

229+
/**
230+
* Util to get a message in the conversation sent by a given user
231+
* @param messageContent Optional parameter to specify content the message should contain. If undefined the last message sent by the user will be returned.
232+
*/
233+
getMessageFromUser(user: User, messageContent?: string) {
234+
const messagesFromUser = this.messageItems.filter({
235+
has: this.page.getByTestId('sender-name').getByText(user.fullName),
236+
});
237+
if (messageContent !== undefined) {
238+
return messagesFromUser.filter({hasText: messageContent});
239+
}
240+
return messagesFromUser.last();
241+
}
242+
243+
/**
244+
* Open the options associated with a message
245+
* @returns the Locator of the now open context menu
246+
*/
247+
async openMessageOptions(message: Locator) {
248+
await message.hover();
249+
await message.getByTestId('message-actions').getByTestId('go-options').click();
250+
// The context menu containing the edit button is positioned globally as an overlay
251+
return this.page.getByRole('menu');
252+
}
253+
254+
/** Click the "Edit" option within a messages options putting it into the message input so it can be updated */
255+
async editMessage(message: Locator) {
256+
const menu = await this.openMessageOptions(message);
257+
await menu.getByRole('button', {name: 'Edit'}).click();
258+
}
259+
260+
async openMessageDetails(message: Locator) {
261+
const menu = await this.openMessageOptions(message);
262+
await menu.getByRole('button', {name: 'Details'}).click();
263+
}
264+
227265
async reactOnMessage(message: Locator, emojiType: EmojiReaction) {
228266
await message.hover();
229267
const reactionButton = message.getByRole('group').getByRole('button').first();

test/e2e_tests/pageManager/webapp/pages/conversationList.page.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -104,7 +104,7 @@ export class ConversationListPage {
104104
await this.createGroupButton.click();
105105
}
106106

107-
private getConversationLocator(conversationName: string) {
107+
getConversationLocator(conversationName: string) {
108108
return this.page.locator(
109109
`${selectByDataAttribute('item-conversation')}${selectByDataAttribute(escapeHtml(conversationName), 'value')}`,
110110
);
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
/*
2+
* Wire
3+
* Copyright (C) 2025 Wire Swiss GmbH
4+
*
5+
* This program is free software: you can redistribute it and/or modify
6+
* it under the terms of the GNU General Public License as published by
7+
* the Free Software Foundation, either version 3 of the License, or
8+
* (at your option) any later version.
9+
*
10+
* This program is distributed in the hope that it will be useful,
11+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
12+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13+
* GNU General Public License for more details.
14+
*
15+
* You should have received a copy of the GNU General Public License
16+
* along with this program. If not, see http://www.gnu.org/licenses/.
17+
*
18+
*/
19+
20+
import {Locator, Page} from '@playwright/test';
21+
22+
/**
23+
* POM for the right sidebar shown when opening the details of a message sent in a group conversation
24+
*/
25+
export class MessageDetailsPage {
26+
readonly page: Page;
27+
readonly component: Locator;
28+
29+
readonly timeEdited: Locator;
30+
31+
constructor(page: Page) {
32+
this.page = page;
33+
this.component = page.locator('#message-details');
34+
35+
this.timeEdited = this.component.getByTestId('status-message-details-edited');
36+
}
37+
}

test/e2e_tests/specs/Accessibility/Accessibility.spec.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,7 @@ test.describe('Accessibility', () => {
8484
await memberPageManagerA.webapp.modals.dataShareConsent().clickDecline();
8585
await memberPageManagerB.webapp.modals.dataShareConsent().clickDecline();
8686

87-
await createGroup(memberPageManagerA, conversationName, [memberB]);
87+
await createGroup(memberPageManagerA.webapp.pages, conversationName, [memberB]);
8888

8989
await navigateToConversation(memberPageManagerA, conversationName);
9090
await navigateToConversation(memberPageManagerB, conversationName);
@@ -150,7 +150,7 @@ test.describe('Accessibility', () => {
150150
await pages.historyInfo().clickConfirmButton();
151151
await components.conversationSidebar().sidebar.waitFor({state: 'visible', timeout: loginTimeOut});
152152

153-
await createGroup(pageManager, conversationName, [memberB]);
153+
await createGroup(pages, conversationName, [memberB]);
154154

155155
await pages.conversation().typeMessage(message);
156156
const page = await pageManager.getPage();

test/e2e_tests/specs/AccountSettingsSpecs/accountSettings.spec.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -237,7 +237,7 @@ test.describe('account settings', () => {
237237

238238
await expect(components.conversationSidebar().personalStatusLabel).toHaveText(memberA.fullName);
239239

240-
await createGroup(pageManager, groupName, [memberB]);
240+
await createGroup(pages, groupName, [memberB]);
241241
// check that the chat is open
242242
expect(await pages.conversationList().isConversationItemVisible(groupName)).toBeTruthy();
243243
await pages.conversation().sendMessage('test');
@@ -260,7 +260,7 @@ test.describe('account settings', () => {
260260

261261
await (await pageManager.getPage()).reload();
262262

263-
await createChannel(pageManager, 'test', [memberB]);
263+
await createChannel(pages, 'test', [memberB]);
264264

265265
await pages.conversation().clickConversationInfoButton();
266266
await expect(pages.conversationDetails().isUserPartOfConversationAsAdmin(memberA.fullName)).toBeTruthy();

test/e2e_tests/specs/ArchiveSpecs/archive.spec.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ test.describe('Accessibility', () => {
110110
const groupName = 'test';
111111
const {components, pages} = pageManager.webapp;
112112
await completeLogin(pageManager, memberA);
113-
await createGroup(pageManager, groupName, [memberB]);
113+
await createGroup(pages, groupName, [memberB]);
114114
await pages.conversation().clickConversationInfoButton();
115115
await pages.conversationDetails().clickArchiveButton();
116116
await pageManager.waitForTimeout(400);

0 commit comments

Comments
 (0)