mirror of
https://github.com/matrix-org/mjolnir.git
synced 2024-10-01 01:36:06 -04:00
Add regression test for timeline pagination.
This commit is contained in:
parent
06e5f00b2d
commit
4e8315be44
@ -12,7 +12,7 @@
|
|||||||
"lint": "tslint --project ./tsconfig.json -t stylish",
|
"lint": "tslint --project ./tsconfig.json -t stylish",
|
||||||
"start:dev": "yarn build && node lib/index.js",
|
"start:dev": "yarn build && node lib/index.js",
|
||||||
"test": "ts-mocha --project ./tsconfig.json test/commands/**/*.ts",
|
"test": "ts-mocha --project ./tsconfig.json test/commands/**/*.ts",
|
||||||
"test:integration": "NODE_ENV=harness ts-mocha --require test/integration/fixtures.ts --project ./tsconfig.json test/integration/**/*Test.ts",
|
"test:integration": "NODE_ENV=harness ts-mocha --require test/integration/fixtures.ts --project ./tsconfig.json \"test/integration/**/*Test.ts\"",
|
||||||
"test:manual": "NODE_ENV=harness ts-node test/integration/manualLaunchScript.ts"
|
"test:manual": "NODE_ENV=harness ts-node test/integration/manualLaunchScript.ts"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
97
test/integration/timelinePaginationTest.ts
Normal file
97
test/integration/timelinePaginationTest.ts
Normal file
@ -0,0 +1,97 @@
|
|||||||
|
import { strict as assert } from "assert";
|
||||||
|
|
||||||
|
import { newTestUser } from "./clientHelper";
|
||||||
|
import { getMessagesByUserIn } from "../../src/utils";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Ensure that Mjolnir paginates only the necessary segment of the room timeline when backfilling.
|
||||||
|
*/
|
||||||
|
describe("Test: timeline pagination", function () {
|
||||||
|
it('does not paginate across the entire room history while backfilling.', async function() {
|
||||||
|
this.timeout(20000);
|
||||||
|
// Create a few users and a room.
|
||||||
|
let badUser = await newTestUser(false, "spammer");
|
||||||
|
let badUserId = await badUser.getUserId();
|
||||||
|
let moderator = await newTestUser(false, "moderator");
|
||||||
|
let targetRoom = await moderator.createRoom({ invite: [await badUser.getUserId()]});
|
||||||
|
await badUser.joinRoom(targetRoom);
|
||||||
|
|
||||||
|
// send some irrelevant messages
|
||||||
|
await Promise.all([...Array(200).keys()].map((i) => moderator.sendMessage(targetRoom, {msgtype: 'm.text.', body: `Irrelevant Message #${i}`})));
|
||||||
|
// bad guy sends 5 messages
|
||||||
|
for (let i = 0; i < 5; i++) {
|
||||||
|
await badUser.sendMessage(targetRoom, {msgtype: 'm.text', body: "Very Bad Stuff"});
|
||||||
|
}
|
||||||
|
// send some irrelevant messages
|
||||||
|
await Promise.all([...Array(50).keys()].map((i) => moderator.sendMessage(targetRoom, {msgtype: 'm.text.', body: `Irrelevant Message #${i}`})));
|
||||||
|
// bad guy sends 1 extra message at the most recent edge of the timeline.
|
||||||
|
await badUser.sendMessage(targetRoom, {msgtype: 'm.text', body: "Very Bad Stuff"});
|
||||||
|
// then call this paignator and ensure that we don't go across the entire room history.
|
||||||
|
let cbCount = 0;
|
||||||
|
let eventCount = 0;
|
||||||
|
await getMessagesByUserIn(moderator, badUserId, targetRoom, 1000, function(events) {
|
||||||
|
cbCount += 1;
|
||||||
|
eventCount += events.length;
|
||||||
|
events.map(e => assert.equal(e.sender, badUserId, "All the events should be from the same sender"));
|
||||||
|
});
|
||||||
|
assert.equal(cbCount, 1, "The callback only needs to be called once with all the messages because the events should be filtered.");
|
||||||
|
assert.equal(eventCount, 7, "There shouldn't be any more events (1 member event and 6 messages), and they should all be from the same account.");
|
||||||
|
})
|
||||||
|
it('does not call the callback with an empty array when there are no relevant events', async function() {
|
||||||
|
this.timeout(20000);
|
||||||
|
let badUser = await newTestUser(false, "spammer");
|
||||||
|
let badUserId = await badUser.getUserId();
|
||||||
|
let moderator = await newTestUser(false, "moderator");
|
||||||
|
let targetRoom = await moderator.createRoom();
|
||||||
|
// send some irrelevant messages
|
||||||
|
await Promise.all([...Array(200).keys()].map((i) => moderator.sendMessage(targetRoom, {msgtype: 'm.text.', body: `Irrelevant Message #${i}`})));
|
||||||
|
// The callback should not be called.
|
||||||
|
let cbCount = 0;
|
||||||
|
await getMessagesByUserIn(moderator, badUserId, targetRoom, 1000, (events) => {
|
||||||
|
cbCount += 1;
|
||||||
|
});
|
||||||
|
assert.equal(cbCount, 0, "The callback should never get called");
|
||||||
|
})
|
||||||
|
it("The limit provided is respected", async function() {
|
||||||
|
this.timeout(20000);
|
||||||
|
let badUser = await newTestUser(false, "spammer");
|
||||||
|
let badUserId = await badUser.getUserId();
|
||||||
|
let moderator = await newTestUser(false, "moderator");
|
||||||
|
let targetRoom = await moderator.createRoom({ invite: [await badUser.getUserId()]});
|
||||||
|
await badUser.joinRoom(targetRoom);
|
||||||
|
// send some bad person messages
|
||||||
|
// bad guy sends 5 messages at the start of the timeline
|
||||||
|
for (let i = 0; i < 5; i++) {
|
||||||
|
await badUser.sendMessage(targetRoom, {msgtype: 'm.text', body: "Very Bad Stuff"});
|
||||||
|
}
|
||||||
|
// send some irrelevant messages
|
||||||
|
await Promise.all([...Array(200).keys()].map((i) => moderator.sendMessage(targetRoom, {msgtype: 'm.text.', body: `Irrelevant Message #${i}`})));
|
||||||
|
let cbCount = 0;
|
||||||
|
await getMessagesByUserIn(moderator, "*spammer*", targetRoom, 200, (events) => {
|
||||||
|
cbCount += 1;
|
||||||
|
});
|
||||||
|
// Remember that the limit is the number of events that getMessagesByUserIn has checked against the glob,
|
||||||
|
// not the number of events to provide to the callback.
|
||||||
|
// E.g. we don't want to paginate to the beginning of history just because less than 200 events match the glob,
|
||||||
|
// which is very likely if a user has only just started sending messages.
|
||||||
|
assert.equal(cbCount, 0, "The callback should never be called as the limit should be reached beforehand.");
|
||||||
|
await getMessagesByUserIn(moderator, "*spammer*", targetRoom, 205, (events) => {
|
||||||
|
cbCount += 1;
|
||||||
|
events.map(e => assert.equal(e.sender, badUserId, "All the events should be from the same sender"));
|
||||||
|
});
|
||||||
|
assert.equal(cbCount, 1, "The callback should be called once with events matching the glob.");
|
||||||
|
});
|
||||||
|
it("Gives the events to the callback ordered by youngest first (even more important when the limit is reached halfway through a chunk).", async function() {
|
||||||
|
this.timeout(20000);
|
||||||
|
let moderator = await newTestUser(false, "moderator");
|
||||||
|
let moderatorId = await moderator.getUserId();
|
||||||
|
let targetRoom = await moderator.createRoom();
|
||||||
|
for (let i = 0; i < 20; i++) {
|
||||||
|
await moderator.sendMessage(targetRoom, {msgtype: 'm.text.', body: `${i}`})
|
||||||
|
}
|
||||||
|
await getMessagesByUserIn(moderator, moderatorId, targetRoom, 5, (events) => {
|
||||||
|
let messageNumbers = events.map(event => parseInt(event.content.body, 10));
|
||||||
|
messageNumbers.map(n => assert.equal(n >= 15, true, "The youngest events should be given to the callback first."))
|
||||||
|
});
|
||||||
|
})
|
||||||
|
});
|
Loading…
Reference in New Issue
Block a user