Signal-Desktop/ts/test-mock/storage/pin_unpin_test.ts

161 lines
4.7 KiB
TypeScript

// Copyright 2022 Signal Messenger, LLC
// SPDX-License-Identifier: AGPL-3.0-only
/* eslint-disable no-await-in-loop */
import { assert } from 'chai';
import type { Group } from '@signalapp/mock-server';
import * as durations from '../../util/durations';
import type { App, Bootstrap } from './fixtures';
import { initStorage, debug } from './fixtures';
describe('storage service', function needsName() {
this.timeout(durations.MINUTE);
let bootstrap: Bootstrap;
let app: App;
let group: Group;
beforeEach(async () => {
({ bootstrap, app, group } = await initStorage());
});
afterEach(async () => {
await app.close();
await bootstrap.teardown();
});
it('should pin/unpin groups', async () => {
const { phone, desktop, contacts } = bootstrap;
const window = await app.getWindow();
const leftPane = window.locator('.left-pane-wrapper');
const conversationStack = window.locator('.conversation-stack');
debug('Verifying that the group is pinned on startup');
await leftPane
.locator(
'_react=ConversationListItem' +
'[isPinned = true] ' +
`[title = ${JSON.stringify(group.title)}]`
)
.waitFor();
debug('Unpinning group via storage service');
{
const state = await phone.expectStorageState('initial state');
await phone.setStorageState(state.unpinGroup(group));
await phone.sendFetchStorage({
timestamp: bootstrap.getTimestamp(),
});
await leftPane
.locator(
'_react=ConversationListItem' +
'[isPinned = false] ' +
`[title = ${JSON.stringify(group.title)}]`
)
.waitFor();
}
debug('Pinning group in the app');
{
const state = await phone.expectStorageState('consistency check');
const convo = leftPane.locator(
'_react=ConversationListItem' +
'[isPinned = false] ' +
`[title = ${JSON.stringify(group.title)}]`
);
await convo.click();
const moreButton = conversationStack.locator(
'button.module-ConversationHeader__button--more'
);
await moreButton.click();
const pinButton = conversationStack.locator(
'.react-contextmenu-item >> "Pin Conversation"'
);
await pinButton.click();
const newState = await phone.waitForStorageState({
after: state,
});
assert.isTrue(await newState.isGroupPinned(group), 'group not pinned');
// AccountRecord
const { added, removed } = newState.diff(state);
assert.strictEqual(added.length, 1, 'only one record must be added');
assert.strictEqual(removed.length, 1, 'only one record must be removed');
}
debug('Pinning > 4 conversations');
{
// We already have one group and first contact pinned so we need three
// more.
const toPin = contacts.slice(1, 4);
// To do that we need them to appear in the left pane, though.
for (const [i, contact] of toPin.entries()) {
const isLast = i === toPin.length - 1;
debug('sending a message to contact=%d', i);
await contact.sendText(desktop, 'Hello!', {
timestamp: bootstrap.getTimestamp(),
});
const state = await phone.expectStorageState('consistency check');
debug('pinning contact=%d', i);
const convo = leftPane.locator(
'_react=ConversationListItem' +
`[title = ${JSON.stringify(contact.profileName)}]`
);
await convo.click();
const moreButton = conversationStack.locator(
'button.module-ConversationHeader__button--more'
);
await moreButton.click();
const pinButton = conversationStack.locator(
'.react-contextmenu-item >> "Pin Conversation"'
);
await pinButton.click();
if (isLast) {
// Storage state shouldn't be updated because we failed to pin
await window
.locator('.Toast >> "You can only pin up to 4 chats"')
.waitFor();
break;
}
debug('verifying storage state change contact=%d', i);
const newState = await phone.waitForStorageState({
after: state,
});
assert.isTrue(await newState.isPinned(contact), 'contact not pinned');
// AccountRecord
const { added, removed } = newState.diff(state);
assert.strictEqual(added.length, 1, 'only one record must be added');
assert.strictEqual(
removed.length,
1,
'only one record must be removed'
);
}
}
debug('Verifying the final manifest version');
const finalState = await phone.expectStorageState('consistency check');
assert.strictEqual(finalState.version, 5);
});
});