You've already forked matrix-js-sdk
mirror of
https://github.com/matrix-org/matrix-js-sdk.git
synced 2025-07-31 15:24:23 +03:00
Add matrix-org/jest
linting (#2973)
This commit is contained in:
19
.eslintrc.js
19
.eslintrc.js
@ -1,6 +1,6 @@
|
|||||||
module.exports = {
|
module.exports = {
|
||||||
plugins: ["matrix-org", "import", "jsdoc"],
|
plugins: ["matrix-org", "import", "jsdoc"],
|
||||||
extends: ["plugin:matrix-org/babel", "plugin:import/typescript"],
|
extends: ["plugin:matrix-org/babel", "plugin:matrix-org/jest", "plugin:import/typescript"],
|
||||||
parserOptions: {
|
parserOptions: {
|
||||||
project: ["./tsconfig.json"],
|
project: ["./tsconfig.json"],
|
||||||
},
|
},
|
||||||
@ -63,6 +63,23 @@ module.exports = {
|
|||||||
],
|
],
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
// Disabled tests are a reality for now but as soon as all of the xits are
|
||||||
|
// eliminated, we should enforce this.
|
||||||
|
"jest/no-disabled-tests": "off",
|
||||||
|
// TODO: There are many tests with invalid expects that should be fixed,
|
||||||
|
// https://github.com/matrix-org/matrix-js-sdk/issues/2976
|
||||||
|
"jest/valid-expect": "off",
|
||||||
|
// TODO: There are many cases to refactor away,
|
||||||
|
// https://github.com/matrix-org/matrix-js-sdk/issues/2978
|
||||||
|
"jest/no-conditional-expect": "off",
|
||||||
|
// Also treat "oldBackendOnly" as a test function.
|
||||||
|
// Used in some crypto tests.
|
||||||
|
"jest/no-standalone-expect": [
|
||||||
|
"error",
|
||||||
|
{
|
||||||
|
additionalTestBlockFunctions: ["beforeAll", "beforeEach", "oldBackendOnly"],
|
||||||
|
},
|
||||||
|
],
|
||||||
},
|
},
|
||||||
overrides: [
|
overrides: [
|
||||||
{
|
{
|
||||||
|
@ -103,8 +103,9 @@
|
|||||||
"eslint-config-prettier": "^8.5.0",
|
"eslint-config-prettier": "^8.5.0",
|
||||||
"eslint-import-resolver-typescript": "^3.5.1",
|
"eslint-import-resolver-typescript": "^3.5.1",
|
||||||
"eslint-plugin-import": "^2.26.0",
|
"eslint-plugin-import": "^2.26.0",
|
||||||
|
"eslint-plugin-jest": "^27.1.6",
|
||||||
"eslint-plugin-jsdoc": "^39.6.4",
|
"eslint-plugin-jsdoc": "^39.6.4",
|
||||||
"eslint-plugin-matrix-org": "^0.10.0",
|
"eslint-plugin-matrix-org": "^1.0.0",
|
||||||
"eslint-plugin-tsdoc": "^0.2.17",
|
"eslint-plugin-tsdoc": "^0.2.17",
|
||||||
"eslint-plugin-unicorn": "^45.0.0",
|
"eslint-plugin-unicorn": "^45.0.0",
|
||||||
"exorcist": "^2.0.0",
|
"exorcist": "^2.0.0",
|
||||||
|
@ -16,6 +16,9 @@ See the License for the specific language governing permissions and
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
// `expect` is allowed in helper functions which are called within `test`/`it` blocks
|
||||||
|
/* eslint-disable jest/no-standalone-expect */
|
||||||
|
|
||||||
// load olm before the sdk if possible
|
// load olm before the sdk if possible
|
||||||
import "./olm-loader";
|
import "./olm-loader";
|
||||||
|
|
||||||
|
@ -743,10 +743,8 @@ describe.each(Object.entries(CRYPTO_BACKENDS))("megolm (%s)", (backend: string,
|
|||||||
describe("get|setGlobalErrorOnUnknownDevices", () => {
|
describe("get|setGlobalErrorOnUnknownDevices", () => {
|
||||||
it("should raise an error if crypto is disabled", () => {
|
it("should raise an error if crypto is disabled", () => {
|
||||||
aliceTestClient.client["cryptoBackend"] = undefined;
|
aliceTestClient.client["cryptoBackend"] = undefined;
|
||||||
expect(() => aliceTestClient.client.setGlobalErrorOnUnknownDevices(true)).toThrowError(
|
expect(() => aliceTestClient.client.setGlobalErrorOnUnknownDevices(true)).toThrow("encryption disabled");
|
||||||
"encryption disabled",
|
expect(() => aliceTestClient.client.getGlobalErrorOnUnknownDevices()).toThrow("encryption disabled");
|
||||||
);
|
|
||||||
expect(() => aliceTestClient.client.getGlobalErrorOnUnknownDevices()).toThrowError("encryption disabled");
|
|
||||||
});
|
});
|
||||||
|
|
||||||
oldBackendOnly("should permit sending to unknown devices", async () => {
|
oldBackendOnly("should permit sending to unknown devices", async () => {
|
||||||
@ -799,12 +797,10 @@ describe.each(Object.entries(CRYPTO_BACKENDS))("megolm (%s)", (backend: string,
|
|||||||
describe("get|setGlobalBlacklistUnverifiedDevices", () => {
|
describe("get|setGlobalBlacklistUnverifiedDevices", () => {
|
||||||
it("should raise an error if crypto is disabled", () => {
|
it("should raise an error if crypto is disabled", () => {
|
||||||
aliceTestClient.client["cryptoBackend"] = undefined;
|
aliceTestClient.client["cryptoBackend"] = undefined;
|
||||||
expect(() => aliceTestClient.client.setGlobalBlacklistUnverifiedDevices(true)).toThrowError(
|
expect(() => aliceTestClient.client.setGlobalBlacklistUnverifiedDevices(true)).toThrow(
|
||||||
"encryption disabled",
|
|
||||||
);
|
|
||||||
expect(() => aliceTestClient.client.getGlobalBlacklistUnverifiedDevices()).toThrowError(
|
|
||||||
"encryption disabled",
|
"encryption disabled",
|
||||||
);
|
);
|
||||||
|
expect(() => aliceTestClient.client.getGlobalBlacklistUnverifiedDevices()).toThrow("encryption disabled");
|
||||||
});
|
});
|
||||||
|
|
||||||
oldBackendOnly("should disable sending to unverified devices", async () => {
|
oldBackendOnly("should disable sending to unverified devices", async () => {
|
||||||
|
@ -175,7 +175,7 @@ describe("MatrixClient events", function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should emit User events", function (done) {
|
it("should emit User events", async () => {
|
||||||
httpBackend!.when("GET", "/sync").respond(200, SYNC_DATA);
|
httpBackend!.when("GET", "/sync").respond(200, SYNC_DATA);
|
||||||
httpBackend!.when("GET", "/sync").respond(200, NEXT_SYNC_DATA);
|
httpBackend!.when("GET", "/sync").respond(200, NEXT_SYNC_DATA);
|
||||||
let fired = false;
|
let fired = false;
|
||||||
@ -192,10 +192,8 @@ describe("MatrixClient events", function () {
|
|||||||
});
|
});
|
||||||
client!.startClient();
|
client!.startClient();
|
||||||
|
|
||||||
httpBackend!.flushAllExpected().then(function () {
|
await httpBackend!.flushAllExpected();
|
||||||
expect(fired).toBe(true);
|
expect(fired).toBe(true);
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should emit Room events", function () {
|
it("should emit Room events", function () {
|
||||||
|
@ -205,19 +205,17 @@ describe("MatrixClient", function () {
|
|||||||
describe("getFilter", function () {
|
describe("getFilter", function () {
|
||||||
const filterId = "f1lt3r1d";
|
const filterId = "f1lt3r1d";
|
||||||
|
|
||||||
it("should return a filter from the store if allowCached", function (done) {
|
it("should return a filter from the store if allowCached", async () => {
|
||||||
const filter = Filter.fromJson(userId, filterId, {
|
const filter = Filter.fromJson(userId, filterId, {
|
||||||
event_format: "client",
|
event_format: "client",
|
||||||
});
|
});
|
||||||
store!.storeFilter(filter);
|
store!.storeFilter(filter);
|
||||||
client!.getFilter(userId, filterId, true).then(function (gotFilter) {
|
const gotFilter = await client!.getFilter(userId, filterId, true);
|
||||||
expect(gotFilter).toEqual(filter);
|
expect(gotFilter).toEqual(filter);
|
||||||
done();
|
|
||||||
});
|
|
||||||
httpBackend!.verifyNoOutstandingRequests();
|
httpBackend!.verifyNoOutstandingRequests();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should do an HTTP request if !allowCached even if one exists", function (done) {
|
it("should do an HTTP request if !allowCached even if one exists", async () => {
|
||||||
const httpFilterDefinition = {
|
const httpFilterDefinition = {
|
||||||
event_format: "federation",
|
event_format: "federation",
|
||||||
};
|
};
|
||||||
@ -230,15 +228,11 @@ describe("MatrixClient", function () {
|
|||||||
event_format: "client",
|
event_format: "client",
|
||||||
});
|
});
|
||||||
store!.storeFilter(storeFilter);
|
store!.storeFilter(storeFilter);
|
||||||
client!.getFilter(userId, filterId, false).then(function (gotFilter) {
|
const [gotFilter] = await Promise.all([client!.getFilter(userId, filterId, false), httpBackend!.flush("")]);
|
||||||
expect(gotFilter.getDefinition()).toEqual(httpFilterDefinition);
|
expect(gotFilter.getDefinition()).toEqual(httpFilterDefinition);
|
||||||
done();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
httpBackend!.flush("");
|
it("should do an HTTP request if nothing is in the cache and then store it", async () => {
|
||||||
});
|
|
||||||
|
|
||||||
it("should do an HTTP request if nothing is in the cache and then store it", function (done) {
|
|
||||||
const httpFilterDefinition = {
|
const httpFilterDefinition = {
|
||||||
event_format: "federation",
|
event_format: "federation",
|
||||||
};
|
};
|
||||||
@ -247,20 +241,16 @@ describe("MatrixClient", function () {
|
|||||||
httpBackend!
|
httpBackend!
|
||||||
.when("GET", "/user/" + encodeURIComponent(userId) + "/filter/" + filterId)
|
.when("GET", "/user/" + encodeURIComponent(userId) + "/filter/" + filterId)
|
||||||
.respond(200, httpFilterDefinition);
|
.respond(200, httpFilterDefinition);
|
||||||
client!.getFilter(userId, filterId, true).then(function (gotFilter) {
|
const [gotFilter] = await Promise.all([client!.getFilter(userId, filterId, true), httpBackend!.flush("")]);
|
||||||
expect(gotFilter.getDefinition()).toEqual(httpFilterDefinition);
|
expect(gotFilter.getDefinition()).toEqual(httpFilterDefinition);
|
||||||
expect(store!.getFilter(userId, filterId)).toBeTruthy();
|
expect(store!.getFilter(userId, filterId)).toBeTruthy();
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
httpBackend!.flush("");
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("createFilter", function () {
|
describe("createFilter", function () {
|
||||||
const filterId = "f1llllllerid";
|
const filterId = "f1llllllerid";
|
||||||
|
|
||||||
it("should do an HTTP request and then store the filter", function (done) {
|
it("should do an HTTP request and then store the filter", async () => {
|
||||||
expect(store!.getFilter(userId, filterId)).toBe(null);
|
expect(store!.getFilter(userId, filterId)).toBe(null);
|
||||||
|
|
||||||
const filterDefinition = {
|
const filterDefinition = {
|
||||||
@ -276,13 +266,9 @@ describe("MatrixClient", function () {
|
|||||||
filter_id: filterId,
|
filter_id: filterId,
|
||||||
});
|
});
|
||||||
|
|
||||||
client!.createFilter(filterDefinition).then(function (gotFilter) {
|
const [gotFilter] = await Promise.all([client!.createFilter(filterDefinition), httpBackend!.flush("")]);
|
||||||
expect(gotFilter.getDefinition()).toEqual(filterDefinition);
|
expect(gotFilter.getDefinition()).toEqual(filterDefinition);
|
||||||
expect(store!.getFilter(userId, filterId)).toEqual(gotFilter);
|
expect(store!.getFilter(userId, filterId)).toEqual(gotFilter);
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
httpBackend!.flush("");
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -94,16 +94,16 @@ describe("MatrixClient opts", function () {
|
|||||||
client.stopClient();
|
client.stopClient();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should be able to send messages", function (done) {
|
it("should be able to send messages", async () => {
|
||||||
const eventId = "$flibble:wibble";
|
const eventId = "$flibble:wibble";
|
||||||
httpBackend.when("PUT", "/txn1").respond(200, {
|
httpBackend.when("PUT", "/txn1").respond(200, {
|
||||||
event_id: eventId,
|
event_id: eventId,
|
||||||
});
|
});
|
||||||
client.sendTextMessage("!foo:bar", "a body", "txn1").then(function (res) {
|
const [res] = await Promise.all([
|
||||||
|
client.sendTextMessage("!foo:bar", "a body", "txn1"),
|
||||||
|
httpBackend.flush("/txn1", 1),
|
||||||
|
]);
|
||||||
expect(res.event_id).toEqual(eventId);
|
expect(res.event_id).toEqual(eventId);
|
||||||
done();
|
|
||||||
});
|
|
||||||
httpBackend.flush("/txn1", 1);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should be able to sync / get new events", async function () {
|
it("should be able to sync / get new events", async function () {
|
||||||
@ -149,7 +149,7 @@ describe("MatrixClient opts", function () {
|
|||||||
client.stopClient();
|
client.stopClient();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("shouldn't retry sending events", function (done) {
|
it("shouldn't retry sending events", async () => {
|
||||||
httpBackend.when("PUT", "/txn1").respond(
|
httpBackend.when("PUT", "/txn1").respond(
|
||||||
500,
|
500,
|
||||||
new MatrixError({
|
new MatrixError({
|
||||||
@ -157,19 +157,17 @@ describe("MatrixClient opts", function () {
|
|||||||
error: "Ruh roh",
|
error: "Ruh roh",
|
||||||
}),
|
}),
|
||||||
);
|
);
|
||||||
client.sendTextMessage("!foo:bar", "a body", "txn1").then(
|
try {
|
||||||
function (res) {
|
await Promise.all([
|
||||||
expect(false).toBe(true);
|
expect(client.sendTextMessage("!foo:bar", "a body", "txn1")).rejects.toThrow(),
|
||||||
},
|
httpBackend.flush("/txn1", 1),
|
||||||
function (err) {
|
]);
|
||||||
expect(err.errcode).toEqual("M_SOMETHING");
|
} catch (err) {
|
||||||
done();
|
expect((<MatrixError>err).errcode).toEqual("M_SOMETHING");
|
||||||
},
|
}
|
||||||
);
|
|
||||||
httpBackend.flush("/txn1", 1);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("shouldn't queue events", function (done) {
|
it("shouldn't queue events", async () => {
|
||||||
httpBackend.when("PUT", "/txn1").respond(200, {
|
httpBackend.when("PUT", "/txn1").respond(200, {
|
||||||
event_id: "AAA",
|
event_id: "AAA",
|
||||||
});
|
});
|
||||||
@ -178,30 +176,38 @@ describe("MatrixClient opts", function () {
|
|||||||
});
|
});
|
||||||
let sentA = false;
|
let sentA = false;
|
||||||
let sentB = false;
|
let sentB = false;
|
||||||
client.sendTextMessage("!foo:bar", "a body", "txn1").then(function (res) {
|
const messageASendPromise = client.sendTextMessage("!foo:bar", "a body", "txn1").then(function (res) {
|
||||||
sentA = true;
|
sentA = true;
|
||||||
|
// We expect messageB to be sent before messageA to ensure as we're
|
||||||
|
// testing that there is no queueing that blocks each other
|
||||||
expect(sentB).toBe(true);
|
expect(sentB).toBe(true);
|
||||||
});
|
});
|
||||||
client.sendTextMessage("!foo:bar", "b body", "txn2").then(function (res) {
|
const messageBSendPromise = client.sendTextMessage("!foo:bar", "b body", "txn2").then(function (res) {
|
||||||
sentB = true;
|
sentB = true;
|
||||||
|
// We expect messageB to be sent before messageA to ensure as we're
|
||||||
|
// testing that there is no queueing that blocks each other
|
||||||
expect(sentA).toBe(false);
|
expect(sentA).toBe(false);
|
||||||
});
|
});
|
||||||
httpBackend.flush("/txn2", 1).then(function () {
|
// Allow messageB to succeed first
|
||||||
httpBackend.flush("/txn1", 1).then(function () {
|
await httpBackend.flush("/txn2", 1);
|
||||||
done();
|
// Then allow messageA to succeed
|
||||||
});
|
await httpBackend.flush("/txn1", 1);
|
||||||
});
|
|
||||||
|
// Now await the message send promises to
|
||||||
|
await messageBSendPromise;
|
||||||
|
await messageASendPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should be able to send messages", function (done) {
|
it("should be able to send messages", async () => {
|
||||||
httpBackend.when("PUT", "/txn1").respond(200, {
|
httpBackend.when("PUT", "/txn1").respond(200, {
|
||||||
event_id: "foo",
|
event_id: "foo",
|
||||||
});
|
});
|
||||||
client.sendTextMessage("!foo:bar", "a body", "txn1").then(function (res) {
|
const [res] = await Promise.all([
|
||||||
|
client.sendTextMessage("!foo:bar", "a body", "txn1"),
|
||||||
|
httpBackend.flush("/txn1", 1),
|
||||||
|
]);
|
||||||
|
|
||||||
expect(res.event_id).toEqual("foo");
|
expect(res.event_id).toEqual("foo");
|
||||||
done();
|
|
||||||
});
|
|
||||||
httpBackend.flush("/txn1", 1);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -48,13 +48,13 @@ describe("MatrixClient retrying", function () {
|
|||||||
return httpBackend!.stop();
|
return httpBackend!.stop();
|
||||||
});
|
});
|
||||||
|
|
||||||
xit("should retry according to MatrixScheduler.retryFn", function () {});
|
it.skip("should retry according to MatrixScheduler.retryFn", function () {});
|
||||||
|
|
||||||
xit("should queue according to MatrixScheduler.queueFn", function () {});
|
it.skip("should queue according to MatrixScheduler.queueFn", function () {});
|
||||||
|
|
||||||
xit("should mark events as EventStatus.NOT_SENT when giving up", function () {});
|
it.skip("should mark events as EventStatus.NOT_SENT when giving up", function () {});
|
||||||
|
|
||||||
xit("should mark events as EventStatus.QUEUED when queued", function () {});
|
it.skip("should mark events as EventStatus.QUEUED when queued", function () {});
|
||||||
|
|
||||||
it("should mark events as EventStatus.CANCELLED when cancelled", function () {
|
it("should mark events as EventStatus.CANCELLED when cancelled", function () {
|
||||||
// send a couple of events; the second will be queued
|
// send a couple of events; the second will be queued
|
||||||
@ -130,7 +130,7 @@ describe("MatrixClient retrying", function () {
|
|||||||
});
|
});
|
||||||
|
|
||||||
describe("resending", function () {
|
describe("resending", function () {
|
||||||
xit("should be able to resend a NOT_SENT event", function () {});
|
it.skip("should be able to resend a NOT_SENT event", function () {});
|
||||||
xit("should be able to resend a sent event", function () {});
|
it.skip("should be able to resend a sent event", function () {});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -163,8 +163,9 @@ describe("MatrixClient room timelines", function () {
|
|||||||
it(
|
it(
|
||||||
"should be added immediately after calling MatrixClient.sendEvent " +
|
"should be added immediately after calling MatrixClient.sendEvent " +
|
||||||
"with EventStatus.SENDING and the right event.sender",
|
"with EventStatus.SENDING and the right event.sender",
|
||||||
function (done) {
|
async () => {
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
const wasMessageAddedPromise = new Promise((resolve) => {
|
||||||
|
client!.on(ClientEvent.Sync, async (state) => {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -181,18 +182,19 @@ describe("MatrixClient room timelines", function () {
|
|||||||
expect(member?.userId).toEqual(userId);
|
expect(member?.userId).toEqual(userId);
|
||||||
expect(member?.name).toEqual(userName);
|
expect(member?.name).toEqual(userName);
|
||||||
|
|
||||||
httpBackend!.flush("/sync", 1).then(function () {
|
await httpBackend!.flush("/sync", 1);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
httpBackend!.flush("/sync", 1);
|
await httpBackend!.flush("/sync", 1);
|
||||||
|
await wasMessageAddedPromise;
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
it(
|
it(
|
||||||
"should be updated correctly when the send request finishes " +
|
"should be updated correctly when the send request finishes " +
|
||||||
"BEFORE the event comes down the event stream",
|
"BEFORE the event comes down the event stream",
|
||||||
function (done) {
|
async () => {
|
||||||
const eventId = "$foo:bar";
|
const eventId = "$foo:bar";
|
||||||
httpBackend!.when("PUT", "/txn1").respond(200, {
|
httpBackend!.when("PUT", "/txn1").respond(200, {
|
||||||
event_id: eventId,
|
event_id: eventId,
|
||||||
@ -207,28 +209,30 @@ describe("MatrixClient room timelines", function () {
|
|||||||
ev.unsigned = { transaction_id: "txn1" };
|
ev.unsigned = { transaction_id: "txn1" };
|
||||||
setNextSyncData([ev]);
|
setNextSyncData([ev]);
|
||||||
|
|
||||||
|
const wasMessageAddedPromise = new Promise((resolve) => {
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
client!.on(ClientEvent.Sync, function (state) {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const room = client!.getRoom(roomId)!;
|
const room = client!.getRoom(roomId)!;
|
||||||
client!.sendTextMessage(roomId, "I am a fish", "txn1").then(function () {
|
client!.sendTextMessage(roomId, "I am a fish", "txn1").then(async () => {
|
||||||
expect(room.timeline[1].getId()).toEqual(eventId);
|
expect(room.timeline[1].getId()).toEqual(eventId);
|
||||||
httpBackend!.flush("/sync", 1).then(function () {
|
await httpBackend!.flush("/sync", 1);
|
||||||
expect(room.timeline[1].getId()).toEqual(eventId);
|
expect(room.timeline[1].getId()).toEqual(eventId);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
|
||||||
});
|
});
|
||||||
httpBackend!.flush("/txn1", 1);
|
httpBackend!.flush("/txn1", 1);
|
||||||
});
|
});
|
||||||
httpBackend!.flush("/sync", 1);
|
});
|
||||||
|
await httpBackend!.flush("/sync", 1);
|
||||||
|
await wasMessageAddedPromise;
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
it(
|
it(
|
||||||
"should be updated correctly when the send request finishes " +
|
"should be updated correctly when the send request finishes " +
|
||||||
"AFTER the event comes down the event stream",
|
"AFTER the event comes down the event stream",
|
||||||
function (done) {
|
async () => {
|
||||||
const eventId = "$foo:bar";
|
const eventId = "$foo:bar";
|
||||||
httpBackend!.when("PUT", "/txn1").respond(200, {
|
httpBackend!.when("PUT", "/txn1").respond(200, {
|
||||||
event_id: eventId,
|
event_id: eventId,
|
||||||
@ -243,23 +247,24 @@ describe("MatrixClient room timelines", function () {
|
|||||||
ev.unsigned = { transaction_id: "txn1" };
|
ev.unsigned = { transaction_id: "txn1" };
|
||||||
setNextSyncData([ev]);
|
setNextSyncData([ev]);
|
||||||
|
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
const wasMessageAddedPromise = new Promise((resolve) => {
|
||||||
|
client!.on(ClientEvent.Sync, async (state) => {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const room = client!.getRoom(roomId)!;
|
const room = client!.getRoom(roomId)!;
|
||||||
const promise = client!.sendTextMessage(roomId, "I am a fish", "txn1");
|
const messageSendPromise = client!.sendTextMessage(roomId, "I am a fish", "txn1");
|
||||||
httpBackend!.flush("/sync", 1).then(function () {
|
await httpBackend!.flush("/sync", 1);
|
||||||
expect(room.timeline.length).toEqual(2);
|
expect(room.timeline.length).toEqual(2);
|
||||||
httpBackend!.flush("/txn1", 1);
|
httpBackend!.flush("/txn1", 1);
|
||||||
promise.then(function () {
|
await messageSendPromise;
|
||||||
expect(room.timeline.length).toEqual(2);
|
expect(room.timeline.length).toEqual(2);
|
||||||
expect(room.timeline[1].getId()).toEqual(eventId);
|
expect(room.timeline[1].getId()).toEqual(eventId);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
await httpBackend!.flush("/sync", 1);
|
||||||
httpBackend!.flush("/sync", 1);
|
await wasMessageAddedPromise;
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
@ -279,30 +284,29 @@ describe("MatrixClient room timelines", function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should set Room.oldState.paginationToken to null at the start" + " of the timeline.", function (done) {
|
it("should set Room.oldState.paginationToken to null at the start of the timeline.", async () => {
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
const didPaginatePromise = new Promise((resolve) => {
|
||||||
|
client!.on(ClientEvent.Sync, async (state) => {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const room = client!.getRoom(roomId)!;
|
const room = client!.getRoom(roomId)!;
|
||||||
expect(room.timeline.length).toEqual(1);
|
expect(room.timeline.length).toEqual(1);
|
||||||
|
|
||||||
client!.scrollback(room).then(function () {
|
await Promise.all([client!.scrollback(room), httpBackend!.flush("/messages", 1)]);
|
||||||
expect(room.timeline.length).toEqual(1);
|
expect(room.timeline.length).toEqual(1);
|
||||||
expect(room.oldState.paginationToken).toBe(null);
|
expect(room.oldState.paginationToken).toBe(null);
|
||||||
|
|
||||||
// still have a sync to flush
|
// still have a sync to flush
|
||||||
httpBackend!.flush("/sync", 1).then(() => {
|
await httpBackend!.flush("/sync", 1);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
await httpBackend!.flush("/sync", 1);
|
||||||
|
await didPaginatePromise;
|
||||||
|
});
|
||||||
|
|
||||||
httpBackend!.flush("/messages", 1);
|
it("should set the right event.sender values", async () => {
|
||||||
});
|
|
||||||
httpBackend!.flush("/sync", 1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("should set the right event.sender values", function (done) {
|
|
||||||
// We're aiming for an eventual timeline of:
|
// We're aiming for an eventual timeline of:
|
||||||
//
|
//
|
||||||
// 'Old Alice' joined the room
|
// 'Old Alice' joined the room
|
||||||
@ -353,7 +357,8 @@ describe("MatrixClient room timelines", function () {
|
|||||||
joinMshipEvent,
|
joinMshipEvent,
|
||||||
];
|
];
|
||||||
|
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
const didPaginatePromise = new Promise((resolve) => {
|
||||||
|
client!.on(ClientEvent.Sync, async (state) => {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -361,7 +366,8 @@ describe("MatrixClient room timelines", function () {
|
|||||||
// sync response
|
// sync response
|
||||||
expect(room.timeline.length).toEqual(1);
|
expect(room.timeline.length).toEqual(1);
|
||||||
|
|
||||||
client!.scrollback(room).then(function () {
|
await Promise.all([client!.scrollback(room), httpBackend!.flush("/messages", 1)]);
|
||||||
|
|
||||||
expect(room.timeline.length).toEqual(5);
|
expect(room.timeline.length).toEqual(5);
|
||||||
const joinMsg = room.timeline[0];
|
const joinMsg = room.timeline[0];
|
||||||
expect(joinMsg.sender?.name).toEqual("Old Alice");
|
expect(joinMsg.sender?.name).toEqual("Old Alice");
|
||||||
@ -371,17 +377,15 @@ describe("MatrixClient room timelines", function () {
|
|||||||
expect(newMsg.sender?.name).toEqual(userName);
|
expect(newMsg.sender?.name).toEqual(userName);
|
||||||
|
|
||||||
// still have a sync to flush
|
// still have a sync to flush
|
||||||
httpBackend!.flush("/sync", 1).then(() => {
|
await httpBackend!.flush("/sync", 1);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
await httpBackend!.flush("/sync", 1);
|
||||||
|
await didPaginatePromise;
|
||||||
|
});
|
||||||
|
|
||||||
httpBackend!.flush("/messages", 1);
|
it("should add it them to the right place in the timeline", async () => {
|
||||||
});
|
|
||||||
httpBackend!.flush("/sync", 1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("should add it them to the right place in the timeline", function (done) {
|
|
||||||
// set the list of events to return on scrollback
|
// set the list of events to return on scrollback
|
||||||
sbEvents = [
|
sbEvents = [
|
||||||
utils.mkMessage({
|
utils.mkMessage({
|
||||||
@ -396,30 +400,30 @@ describe("MatrixClient room timelines", function () {
|
|||||||
}),
|
}),
|
||||||
];
|
];
|
||||||
|
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
const didPaginatePromise = new Promise((resolve) => {
|
||||||
|
client!.on(ClientEvent.Sync, async (state) => {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const room = client!.getRoom(roomId)!;
|
const room = client!.getRoom(roomId)!;
|
||||||
expect(room.timeline.length).toEqual(1);
|
expect(room.timeline.length).toEqual(1);
|
||||||
|
|
||||||
client!.scrollback(room).then(function () {
|
await Promise.all([client!.scrollback(room), httpBackend!.flush("/messages", 1)]);
|
||||||
|
|
||||||
expect(room.timeline.length).toEqual(3);
|
expect(room.timeline.length).toEqual(3);
|
||||||
expect(room.timeline[0].event).toEqual(sbEvents[1]);
|
expect(room.timeline[0].event).toEqual(sbEvents[1]);
|
||||||
expect(room.timeline[1].event).toEqual(sbEvents[0]);
|
expect(room.timeline[1].event).toEqual(sbEvents[0]);
|
||||||
|
|
||||||
// still have a sync to flush
|
// still have a sync to flush
|
||||||
httpBackend!.flush("/sync", 1).then(() => {
|
await httpBackend!.flush("/sync", 1);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
await httpBackend!.flush("/sync", 1);
|
||||||
|
await didPaginatePromise;
|
||||||
|
});
|
||||||
|
|
||||||
httpBackend!.flush("/messages", 1);
|
it("should use 'end' as the next pagination token", async () => {
|
||||||
});
|
|
||||||
httpBackend!.flush("/sync", 1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("should use 'end' as the next pagination token", function (done) {
|
|
||||||
// set the list of events to return on scrollback
|
// set the list of events to return on scrollback
|
||||||
sbEvents = [
|
sbEvents = [
|
||||||
utils.mkMessage({
|
utils.mkMessage({
|
||||||
@ -429,25 +433,24 @@ describe("MatrixClient room timelines", function () {
|
|||||||
}),
|
}),
|
||||||
];
|
];
|
||||||
|
|
||||||
client!.on(ClientEvent.Sync, function (state) {
|
const didPaginatePromise = new Promise((resolve) => {
|
||||||
|
client!.on(ClientEvent.Sync, async (state) => {
|
||||||
if (state !== "PREPARED") {
|
if (state !== "PREPARED") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const room = client!.getRoom(roomId)!;
|
const room = client!.getRoom(roomId)!;
|
||||||
expect(room.oldState.paginationToken).toBeTruthy();
|
expect(room.oldState.paginationToken).toBeTruthy();
|
||||||
|
|
||||||
client!.scrollback(room, 1).then(function () {
|
await Promise.all([client!.scrollback(room, 1), httpBackend!.flush("/messages", 1)]);
|
||||||
expect(room.oldState.paginationToken).toEqual(sbEndTok);
|
expect(room.oldState.paginationToken).toEqual(sbEndTok);
|
||||||
});
|
|
||||||
|
|
||||||
httpBackend!.flush("/messages", 1).then(function () {
|
|
||||||
// still have a sync to flush
|
// still have a sync to flush
|
||||||
httpBackend!.flush("/sync", 1).then(() => {
|
await httpBackend!.flush("/sync", 1);
|
||||||
done();
|
resolve(null);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
await httpBackend!.flush("/sync", 1);
|
||||||
httpBackend!.flush("/sync", 1);
|
await didPaginatePromise;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -81,17 +81,15 @@ describe("MatrixClient syncing", () => {
|
|||||||
presence: {},
|
presence: {},
|
||||||
};
|
};
|
||||||
|
|
||||||
it("should /sync after /pushrules and /filter.", (done) => {
|
it("should /sync after /pushrules and /filter.", async () => {
|
||||||
httpBackend!.when("GET", "/sync").respond(200, syncData);
|
httpBackend!.when("GET", "/sync").respond(200, syncData);
|
||||||
|
|
||||||
client!.startClient();
|
client!.startClient();
|
||||||
|
|
||||||
httpBackend!.flushAllExpected().then(() => {
|
await httpBackend!.flushAllExpected();
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should pass the 'next_batch' token from /sync to the since= param of the next /sync", (done) => {
|
it("should pass the 'next_batch' token from /sync to the since= param of the next /sync", async () => {
|
||||||
httpBackend!.when("GET", "/sync").respond(200, syncData);
|
httpBackend!.when("GET", "/sync").respond(200, syncData);
|
||||||
httpBackend!
|
httpBackend!
|
||||||
.when("GET", "/sync")
|
.when("GET", "/sync")
|
||||||
@ -102,9 +100,7 @@ describe("MatrixClient syncing", () => {
|
|||||||
|
|
||||||
client!.startClient();
|
client!.startClient();
|
||||||
|
|
||||||
httpBackend!.flushAllExpected().then(() => {
|
await httpBackend!.flushAllExpected();
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should emit RoomEvent.MyMembership for invite->leave->invite cycles", async () => {
|
it("should emit RoomEvent.MyMembership for invite->leave->invite cycles", async () => {
|
||||||
@ -724,7 +720,7 @@ describe("MatrixClient syncing", () => {
|
|||||||
// events that arrive in the incremental sync as if they preceeded the
|
// events that arrive in the incremental sync as if they preceeded the
|
||||||
// timeline events, however this breaks peeking, so it's disabled
|
// timeline events, however this breaks peeking, so it's disabled
|
||||||
// (see sync.js)
|
// (see sync.js)
|
||||||
xit("should correctly interpret state in incremental sync.", () => {
|
it.skip("should correctly interpret state in incremental sync.", () => {
|
||||||
httpBackend!.when("GET", "/sync").respond(200, syncData);
|
httpBackend!.when("GET", "/sync").respond(200, syncData);
|
||||||
httpBackend!.when("GET", "/sync").respond(200, nextSyncData);
|
httpBackend!.when("GET", "/sync").respond(200, nextSyncData);
|
||||||
|
|
||||||
@ -741,9 +737,9 @@ describe("MatrixClient syncing", () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
xit("should update power levels for users in a room", () => {});
|
it.skip("should update power levels for users in a room", () => {});
|
||||||
|
|
||||||
xit("should update the room topic", () => {});
|
it.skip("should update the room topic", () => {});
|
||||||
|
|
||||||
describe("onMarkerStateEvent", () => {
|
describe("onMarkerStateEvent", () => {
|
||||||
const normalMessageEvent = utils.mkMessage({
|
const normalMessageEvent = utils.mkMessage({
|
||||||
@ -840,6 +836,7 @@ describe("MatrixClient syncing", () => {
|
|||||||
roomVersion: "org.matrix.msc2716v3",
|
roomVersion: "org.matrix.msc2716v3",
|
||||||
},
|
},
|
||||||
].forEach((testMeta) => {
|
].forEach((testMeta) => {
|
||||||
|
// eslint-disable-next-line jest/valid-title
|
||||||
describe(testMeta.label, () => {
|
describe(testMeta.label, () => {
|
||||||
const roomCreateEvent = utils.mkEvent({
|
const roomCreateEvent = utils.mkEvent({
|
||||||
type: "m.room.create",
|
type: "m.room.create",
|
||||||
@ -1592,27 +1589,24 @@ describe("MatrixClient syncing", () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
describe("of a room", () => {
|
describe("of a room", () => {
|
||||||
xit(
|
it.skip(
|
||||||
"should sync when a join event (which changes state) for the user" +
|
"should sync when a join event (which changes state) for the user" +
|
||||||
" arrives down the event stream (e.g. join from another device)",
|
" arrives down the event stream (e.g. join from another device)",
|
||||||
() => {},
|
() => {},
|
||||||
);
|
);
|
||||||
|
|
||||||
xit("should sync when the user explicitly calls joinRoom", () => {});
|
it.skip("should sync when the user explicitly calls joinRoom", () => {});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("syncLeftRooms", () => {
|
describe("syncLeftRooms", () => {
|
||||||
beforeEach((done) => {
|
beforeEach(async () => {
|
||||||
client!.startClient();
|
client!.startClient();
|
||||||
|
|
||||||
httpBackend!.flushAllExpected().then(() => {
|
await httpBackend!.flushAllExpected();
|
||||||
// the /sync call from syncLeftRooms ends up in the request
|
// the /sync call from syncLeftRooms ends up in the request
|
||||||
// queue behind the call from the running client; add a response
|
// queue behind the call from the running client; add a response
|
||||||
// to flush the client's one out.
|
// to flush the client's one out.
|
||||||
httpBackend!.when("GET", "/sync").respond(200, {});
|
await httpBackend!.when("GET", "/sync").respond(200, {});
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should create and use an appropriate filter", () => {
|
it("should create and use an appropriate filter", () => {
|
||||||
|
@ -153,11 +153,11 @@ describe("SlidingSyncSdk", () => {
|
|||||||
const hasSynced = sdk!.sync();
|
const hasSynced = sdk!.sync();
|
||||||
await httpBackend!.flushAllExpected();
|
await httpBackend!.flushAllExpected();
|
||||||
await hasSynced;
|
await hasSynced;
|
||||||
expect(mockSlidingSync!.start).toBeCalled();
|
expect(mockSlidingSync!.start).toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
it("can stop()", async () => {
|
it("can stop()", async () => {
|
||||||
sdk!.stop();
|
sdk!.stop();
|
||||||
expect(mockSlidingSync!.stop).toBeCalled();
|
expect(mockSlidingSync!.stop).toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -584,7 +584,7 @@ describe("SlidingSyncSdk", () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it("emits SyncState.Error immediately when receiving M_UNKNOWN_TOKEN and stops syncing", async () => {
|
it("emits SyncState.Error immediately when receiving M_UNKNOWN_TOKEN and stops syncing", async () => {
|
||||||
expect(mockSlidingSync!.stop).not.toBeCalled();
|
expect(mockSlidingSync!.stop).not.toHaveBeenCalled();
|
||||||
mockSlidingSync!.emit(
|
mockSlidingSync!.emit(
|
||||||
SlidingSyncEvent.Lifecycle,
|
SlidingSyncEvent.Lifecycle,
|
||||||
SlidingSyncState.RequestFinished,
|
SlidingSyncState.RequestFinished,
|
||||||
@ -595,7 +595,7 @@ describe("SlidingSyncSdk", () => {
|
|||||||
}),
|
}),
|
||||||
);
|
);
|
||||||
expect(sdk!.getSyncState()).toEqual(SyncState.Error);
|
expect(sdk!.getSyncState()).toEqual(SyncState.Error);
|
||||||
expect(mockSlidingSync!.stop).toBeCalled();
|
expect(mockSlidingSync!.stop).toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -5,6 +5,7 @@ import { getMockClientWithEventEmitter } from "../test-utils/client";
|
|||||||
import { StubStore } from "../../src/store/stub";
|
import { StubStore } from "../../src/store/stub";
|
||||||
import { IndexedToDeviceBatch } from "../../src/models/ToDeviceMessage";
|
import { IndexedToDeviceBatch } from "../../src/models/ToDeviceMessage";
|
||||||
import { SyncState } from "../../src/sync";
|
import { SyncState } from "../../src/sync";
|
||||||
|
import { defer } from "../../src/utils";
|
||||||
|
|
||||||
describe("onResumedSync", () => {
|
describe("onResumedSync", () => {
|
||||||
let batch: IndexedToDeviceBatch | null;
|
let batch: IndexedToDeviceBatch | null;
|
||||||
@ -58,7 +59,9 @@ describe("onResumedSync", () => {
|
|||||||
queue = new ToDeviceMessageQueue(mockClient);
|
queue = new ToDeviceMessageQueue(mockClient);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("resends queue after connectivity restored", (done) => {
|
it("resends queue after connectivity restored", async () => {
|
||||||
|
const deferred = defer();
|
||||||
|
|
||||||
onSendToDeviceFailure = () => {
|
onSendToDeviceFailure = () => {
|
||||||
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
||||||
expect(store.removeToDeviceBatch).not.toHaveBeenCalled();
|
expect(store.removeToDeviceBatch).not.toHaveBeenCalled();
|
||||||
@ -70,26 +73,32 @@ describe("onResumedSync", () => {
|
|||||||
onSendToDeviceSuccess = () => {
|
onSendToDeviceSuccess = () => {
|
||||||
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(3);
|
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(3);
|
||||||
expect(store.removeToDeviceBatch).toHaveBeenCalled();
|
expect(store.removeToDeviceBatch).toHaveBeenCalled();
|
||||||
done();
|
deferred.resolve();
|
||||||
};
|
};
|
||||||
|
|
||||||
queue.start();
|
queue.start();
|
||||||
|
return deferred.promise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("does not resend queue if client sync still catching up", (done) => {
|
it("does not resend queue if client sync still catching up", async () => {
|
||||||
|
const deferred = defer();
|
||||||
|
|
||||||
onSendToDeviceFailure = () => {
|
onSendToDeviceFailure = () => {
|
||||||
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
||||||
expect(store.removeToDeviceBatch).not.toHaveBeenCalled();
|
expect(store.removeToDeviceBatch).not.toHaveBeenCalled();
|
||||||
|
|
||||||
resumeSync(SyncState.Catchup, SyncState.Catchup);
|
resumeSync(SyncState.Catchup, SyncState.Catchup);
|
||||||
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
||||||
done();
|
deferred.resolve();
|
||||||
};
|
};
|
||||||
|
|
||||||
queue.start();
|
queue.start();
|
||||||
|
return deferred.promise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("does not resend queue if connectivity restored after queue stopped", (done) => {
|
it("does not resend queue if connectivity restored after queue stopped", async () => {
|
||||||
|
const deferred = defer();
|
||||||
|
|
||||||
onSendToDeviceFailure = () => {
|
onSendToDeviceFailure = () => {
|
||||||
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
||||||
expect(store.removeToDeviceBatch).not.toHaveBeenCalled();
|
expect(store.removeToDeviceBatch).not.toHaveBeenCalled();
|
||||||
@ -98,9 +107,10 @@ describe("onResumedSync", () => {
|
|||||||
|
|
||||||
resumeSync(SyncState.Syncing, SyncState.Catchup);
|
resumeSync(SyncState.Syncing, SyncState.Catchup);
|
||||||
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
expect(store.getOldestToDeviceBatch).toHaveBeenCalledTimes(1);
|
||||||
done();
|
deferred.resolve();
|
||||||
};
|
};
|
||||||
|
|
||||||
queue.start();
|
queue.start();
|
||||||
|
return deferred.promise;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -550,7 +550,7 @@ describe("Crypto", function () {
|
|||||||
aliceClient.crypto!.outgoingRoomKeyRequestManager.sendQueuedRequests();
|
aliceClient.crypto!.outgoingRoomKeyRequestManager.sendQueuedRequests();
|
||||||
jest.runAllTimers();
|
jest.runAllTimers();
|
||||||
await Promise.resolve();
|
await Promise.resolve();
|
||||||
expect(aliceSendToDevice).toBeCalledTimes(1);
|
expect(aliceSendToDevice).toHaveBeenCalledTimes(1);
|
||||||
const txnId = aliceSendToDevice.mock.calls[0][2];
|
const txnId = aliceSendToDevice.mock.calls[0][2];
|
||||||
|
|
||||||
// give the room key request manager time to update the state
|
// give the room key request manager time to update the state
|
||||||
@ -564,7 +564,7 @@ describe("Crypto", function () {
|
|||||||
// cancelAndResend will call sendToDevice twice:
|
// cancelAndResend will call sendToDevice twice:
|
||||||
// the first call to sendToDevice will be the cancellation
|
// the first call to sendToDevice will be the cancellation
|
||||||
// the second call to sendToDevice will be the key request
|
// the second call to sendToDevice will be the key request
|
||||||
expect(aliceSendToDevice).toBeCalledTimes(3);
|
expect(aliceSendToDevice).toHaveBeenCalledTimes(3);
|
||||||
expect(aliceSendToDevice.mock.calls[2][2]).not.toBe(txnId);
|
expect(aliceSendToDevice.mock.calls[2][2]).not.toBe(txnId);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -148,6 +148,10 @@ describe("DeviceList", function () {
|
|||||||
dl.invalidateUserDeviceList("@test1:sw1v.org");
|
dl.invalidateUserDeviceList("@test1:sw1v.org");
|
||||||
dl.refreshOutdatedDeviceLists();
|
dl.refreshOutdatedDeviceLists();
|
||||||
|
|
||||||
|
// TODO: Fix this test so we actually await the call and assertions and remove
|
||||||
|
// the eslint disable, https://github.com/matrix-org/matrix-js-sdk/issues/2977
|
||||||
|
//
|
||||||
|
// eslint-disable-next-line jest/valid-expect-in-promise
|
||||||
dl.saveIfDirty()
|
dl.saveIfDirty()
|
||||||
.then(() => {
|
.then(() => {
|
||||||
// the first request completes
|
// the first request completes
|
||||||
@ -196,7 +200,7 @@ describe("DeviceList", function () {
|
|||||||
downloadSpy.mockReturnValueOnce(queryDefer2.promise);
|
downloadSpy.mockReturnValueOnce(queryDefer2.promise);
|
||||||
|
|
||||||
const prom1 = dl.refreshOutdatedDeviceLists();
|
const prom1 = dl.refreshOutdatedDeviceLists();
|
||||||
expect(downloadSpy).toBeCalledTimes(2);
|
expect(downloadSpy).toHaveBeenCalledTimes(2);
|
||||||
expect(downloadSpy).toHaveBeenNthCalledWith(1, ["@test1:sw1v.org"], {});
|
expect(downloadSpy).toHaveBeenNthCalledWith(1, ["@test1:sw1v.org"], {});
|
||||||
expect(downloadSpy).toHaveBeenNthCalledWith(2, ["@test2:sw1v.org"], {});
|
expect(downloadSpy).toHaveBeenNthCalledWith(2, ["@test2:sw1v.org"], {});
|
||||||
queryDefer1.resolve(utils.deepCopy(signedDeviceList));
|
queryDefer1.resolve(utils.deepCopy(signedDeviceList));
|
||||||
|
@ -211,7 +211,7 @@ describe("MegolmDecryption", function () {
|
|||||||
.then(() => {
|
.then(() => {
|
||||||
// check that it called encryptMessageForDevice with
|
// check that it called encryptMessageForDevice with
|
||||||
// appropriate args.
|
// appropriate args.
|
||||||
expect(mockOlmLib.encryptMessageForDevice).toBeCalledTimes(1);
|
expect(mockOlmLib.encryptMessageForDevice).toHaveBeenCalledTimes(1);
|
||||||
|
|
||||||
const call = mockOlmLib.encryptMessageForDevice.mock.calls[0];
|
const call = mockOlmLib.encryptMessageForDevice.mock.calls[0];
|
||||||
const payload = call[6];
|
const payload = call[6];
|
||||||
|
@ -1148,6 +1148,6 @@ describe("userHasCrossSigningKeys", function () {
|
|||||||
|
|
||||||
it("throws an error if crypto is disabled", () => {
|
it("throws an error if crypto is disabled", () => {
|
||||||
aliceClient["cryptoBackend"] = undefined;
|
aliceClient["cryptoBackend"] = undefined;
|
||||||
expect(() => aliceClient.userHasCrossSigningKeys()).toThrowError("encryption disabled");
|
expect(() => aliceClient.userHasCrossSigningKeys()).toThrow("encryption disabled");
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -179,7 +179,7 @@ describe("EventTimelineSet", () => {
|
|||||||
eventTimelineSet.addEventToTimeline(messageEvent, liveTimeline2, {
|
eventTimelineSet.addEventToTimeline(messageEvent, liveTimeline2, {
|
||||||
toStartOfTimeline: true,
|
toStartOfTimeline: true,
|
||||||
});
|
});
|
||||||
}).toThrowError();
|
}).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should not add a threaded reply to the main room timeline", () => {
|
it("should not add a threaded reply to the main room timeline", () => {
|
||||||
@ -399,7 +399,7 @@ describe("EventTimelineSet", () => {
|
|||||||
|
|
||||||
it("should throw if timeline set has no room", () => {
|
it("should throw if timeline set has no room", () => {
|
||||||
const eventTimelineSet = new EventTimelineSet(undefined, {}, client);
|
const eventTimelineSet = new EventTimelineSet(undefined, {}, client);
|
||||||
expect(() => eventTimelineSet.canContain(messageEvent)).toThrowError();
|
expect(() => eventTimelineSet.canContain(messageEvent)).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should return false if timeline set is for thread but event is not threaded", () => {
|
it("should return false if timeline set is for thread but event is not threaded", () => {
|
||||||
|
@ -150,26 +150,6 @@ describe("PollResponseEvent", () => {
|
|||||||
expect(response.spoiled).toBe(true);
|
expect(response.spoiled).toBe(true);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should spoil the vote when answers are empty", () => {
|
|
||||||
const input: IPartialEvent<PollResponseEventContent> = {
|
|
||||||
type: M_POLL_RESPONSE.name,
|
|
||||||
content: {
|
|
||||||
"m.relates_to": {
|
|
||||||
rel_type: REFERENCE_RELATION.name,
|
|
||||||
event_id: "$poll",
|
|
||||||
},
|
|
||||||
[M_POLL_RESPONSE.name]: {
|
|
||||||
answers: [],
|
|
||||||
},
|
|
||||||
},
|
|
||||||
};
|
|
||||||
const response = new PollResponseEvent(input);
|
|
||||||
expect(response.spoiled).toBe(true);
|
|
||||||
|
|
||||||
response.validateAgainst(SAMPLE_POLL);
|
|
||||||
expect(response.spoiled).toBe(true);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("should spoil the vote when answers are not strings", () => {
|
it("should spoil the vote when answers are not strings", () => {
|
||||||
const input: IPartialEvent<PollResponseEventContent> = {
|
const input: IPartialEvent<PollResponseEventContent> = {
|
||||||
type: M_POLL_RESPONSE.name,
|
type: M_POLL_RESPONSE.name,
|
||||||
|
@ -78,8 +78,8 @@ describe("InteractiveAuth", () => {
|
|||||||
|
|
||||||
const res = await ia.attemptAuth();
|
const res = await ia.attemptAuth();
|
||||||
expect(res).toBe(requestRes);
|
expect(res).toBe(requestRes);
|
||||||
expect(doRequest).toBeCalledTimes(1);
|
expect(doRequest).toHaveBeenCalledTimes(1);
|
||||||
expect(stateUpdated).toBeCalledTimes(1);
|
expect(stateUpdated).toHaveBeenCalledTimes(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should handle auth errcode presence", async () => {
|
it("should handle auth errcode presence", async () => {
|
||||||
@ -128,8 +128,8 @@ describe("InteractiveAuth", () => {
|
|||||||
|
|
||||||
const res = await ia.attemptAuth();
|
const res = await ia.attemptAuth();
|
||||||
expect(res).toBe(requestRes);
|
expect(res).toBe(requestRes);
|
||||||
expect(doRequest).toBeCalledTimes(1);
|
expect(doRequest).toHaveBeenCalledTimes(1);
|
||||||
expect(stateUpdated).toBeCalledTimes(1);
|
expect(stateUpdated).toHaveBeenCalledTimes(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should handle set emailSid for email flow", async () => {
|
it("should handle set emailSid for email flow", async () => {
|
||||||
@ -180,9 +180,9 @@ describe("InteractiveAuth", () => {
|
|||||||
|
|
||||||
const res = await ia.attemptAuth();
|
const res = await ia.attemptAuth();
|
||||||
expect(res).toBe(requestRes);
|
expect(res).toBe(requestRes);
|
||||||
expect(doRequest).toBeCalledTimes(1);
|
expect(doRequest).toHaveBeenCalledTimes(1);
|
||||||
expect(stateUpdated).toBeCalledTimes(1);
|
expect(stateUpdated).toHaveBeenCalledTimes(1);
|
||||||
expect(requestEmailToken).toBeCalledTimes(0);
|
expect(requestEmailToken).toHaveBeenCalledTimes(0);
|
||||||
expect(ia.getEmailSid()).toBe("myEmailSid");
|
expect(ia.getEmailSid()).toBe("myEmailSid");
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -244,8 +244,8 @@ describe("InteractiveAuth", () => {
|
|||||||
|
|
||||||
const res = await ia.attemptAuth();
|
const res = await ia.attemptAuth();
|
||||||
expect(res).toBe(requestRes);
|
expect(res).toBe(requestRes);
|
||||||
expect(doRequest).toBeCalledTimes(2);
|
expect(doRequest).toHaveBeenCalledTimes(2);
|
||||||
expect(stateUpdated).toBeCalledTimes(1);
|
expect(stateUpdated).toHaveBeenCalledTimes(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should make a request if authdata is null", async () => {
|
it("should make a request if authdata is null", async () => {
|
||||||
@ -306,8 +306,8 @@ describe("InteractiveAuth", () => {
|
|||||||
|
|
||||||
const res = await ia.attemptAuth();
|
const res = await ia.attemptAuth();
|
||||||
expect(res).toBe(requestRes);
|
expect(res).toBe(requestRes);
|
||||||
expect(doRequest).toBeCalledTimes(2);
|
expect(doRequest).toHaveBeenCalledTimes(2);
|
||||||
expect(stateUpdated).toBeCalledTimes(1);
|
expect(stateUpdated).toHaveBeenCalledTimes(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should start an auth stage and reject if no auth flow", async () => {
|
it("should start an auth stage and reject if no auth flow", async () => {
|
||||||
@ -430,8 +430,8 @@ describe("InteractiveAuth", () => {
|
|||||||
|
|
||||||
const res = await ia.attemptAuth();
|
const res = await ia.attemptAuth();
|
||||||
expect(res).toBe(requestRes);
|
expect(res).toBe(requestRes);
|
||||||
expect(doRequest).toBeCalledTimes(1);
|
expect(doRequest).toHaveBeenCalledTimes(1);
|
||||||
expect(stateUpdated).toBeCalledTimes(0);
|
expect(stateUpdated).toHaveBeenCalledTimes(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("requestEmailToken", () => {
|
describe("requestEmailToken", () => {
|
||||||
@ -464,35 +464,6 @@ describe("InteractiveAuth", () => {
|
|||||||
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 5, undefined);
|
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 5, undefined);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("increases auth attempts", async () => {
|
|
||||||
const doRequest = jest.fn();
|
|
||||||
const stateUpdated = jest.fn();
|
|
||||||
const requestEmailToken = jest.fn();
|
|
||||||
requestEmailToken.mockImplementation(async () => ({ sid: "" }));
|
|
||||||
|
|
||||||
const ia = new InteractiveAuth({
|
|
||||||
matrixClient: getFakeClient(),
|
|
||||||
doRequest,
|
|
||||||
stateUpdated,
|
|
||||||
requestEmailToken,
|
|
||||||
});
|
|
||||||
|
|
||||||
await ia.requestEmailToken();
|
|
||||||
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 1, undefined);
|
|
||||||
requestEmailToken.mockClear();
|
|
||||||
await ia.requestEmailToken();
|
|
||||||
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 2, undefined);
|
|
||||||
requestEmailToken.mockClear();
|
|
||||||
await ia.requestEmailToken();
|
|
||||||
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 3, undefined);
|
|
||||||
requestEmailToken.mockClear();
|
|
||||||
await ia.requestEmailToken();
|
|
||||||
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 4, undefined);
|
|
||||||
requestEmailToken.mockClear();
|
|
||||||
await ia.requestEmailToken();
|
|
||||||
expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 5, undefined);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("passes errors through", async () => {
|
it("passes errors through", async () => {
|
||||||
const doRequest = jest.fn();
|
const doRequest = jest.fn();
|
||||||
const stateUpdated = jest.fn();
|
const stateUpdated = jest.fn();
|
||||||
@ -508,7 +479,7 @@ describe("InteractiveAuth", () => {
|
|||||||
requestEmailToken,
|
requestEmailToken,
|
||||||
});
|
});
|
||||||
|
|
||||||
await expect(ia.requestEmailToken.bind(ia)).rejects.toThrowError("unspecific network error");
|
await expect(ia.requestEmailToken.bind(ia)).rejects.toThrow("unspecific network error");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("only starts one request at a time", async () => {
|
it("only starts one request at a time", async () => {
|
||||||
|
@ -893,7 +893,7 @@ describe("MatrixClient", function () {
|
|||||||
describe("getOrCreateFilter", function () {
|
describe("getOrCreateFilter", function () {
|
||||||
it("should POST createFilter if no id is present in localStorage", function () {});
|
it("should POST createFilter if no id is present in localStorage", function () {});
|
||||||
it("should use an existing filter if id is present in localStorage", function () {});
|
it("should use an existing filter if id is present in localStorage", function () {});
|
||||||
it("should handle localStorage filterId missing from the server", function (done) {
|
it("should handle localStorage filterId missing from the server", async () => {
|
||||||
function getFilterName(userId: string, suffix?: string) {
|
function getFilterName(userId: string, suffix?: string) {
|
||||||
// scope this on the user ID because people may login on many accounts
|
// scope this on the user ID because people may login on many accounts
|
||||||
// and they all need to be stored!
|
// and they all need to be stored!
|
||||||
@ -919,10 +919,8 @@ describe("MatrixClient", function () {
|
|||||||
client.store.setFilterIdByName(filterName, invalidFilterId);
|
client.store.setFilterIdByName(filterName, invalidFilterId);
|
||||||
const filter = new Filter(client.credentials.userId);
|
const filter = new Filter(client.credentials.userId);
|
||||||
|
|
||||||
client.getOrCreateFilter(filterName, filter).then(function (filterId) {
|
const filterId = await client.getOrCreateFilter(filterName, filter);
|
||||||
expect(filterId).toEqual(FILTER_RESPONSE.data?.filter_id);
|
expect(filterId).toEqual(FILTER_RESPONSE.data?.filter_id);
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -933,7 +931,7 @@ describe("MatrixClient", function () {
|
|||||||
expect(client.retryImmediately()).toBe(false);
|
expect(client.retryImmediately()).toBe(false);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should work on /filter", function (done) {
|
it("should work on /filter", async () => {
|
||||||
httpLookups = [];
|
httpLookups = [];
|
||||||
httpLookups.push(PUSH_RULES_RESPONSE);
|
httpLookups.push(PUSH_RULES_RESPONSE);
|
||||||
httpLookups.push({
|
httpLookups.push({
|
||||||
@ -944,6 +942,7 @@ describe("MatrixClient", function () {
|
|||||||
httpLookups.push(FILTER_RESPONSE);
|
httpLookups.push(FILTER_RESPONSE);
|
||||||
httpLookups.push(SYNC_RESPONSE);
|
httpLookups.push(SYNC_RESPONSE);
|
||||||
|
|
||||||
|
const wasPreparedPromise = new Promise((resolve) => {
|
||||||
client.on(ClientEvent.Sync, function syncListener(state) {
|
client.on(ClientEvent.Sync, function syncListener(state) {
|
||||||
if (state === "ERROR" && httpLookups.length > 0) {
|
if (state === "ERROR" && httpLookups.length > 0) {
|
||||||
expect(httpLookups.length).toEqual(2);
|
expect(httpLookups.length).toEqual(2);
|
||||||
@ -951,16 +950,18 @@ describe("MatrixClient", function () {
|
|||||||
jest.advanceTimersByTime(1);
|
jest.advanceTimersByTime(1);
|
||||||
} else if (state === "PREPARED" && httpLookups.length === 0) {
|
} else if (state === "PREPARED" && httpLookups.length === 0) {
|
||||||
client.removeListener(ClientEvent.Sync, syncListener);
|
client.removeListener(ClientEvent.Sync, syncListener);
|
||||||
done();
|
resolve(null);
|
||||||
} else {
|
} else {
|
||||||
// unexpected state transition!
|
// unexpected state transition!
|
||||||
expect(state).toEqual(null);
|
expect(state).toEqual(null);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
client.startClient();
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await wasPreparedPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should work on /sync", function (done) {
|
it("should work on /sync", async () => {
|
||||||
httpLookups.push({
|
httpLookups.push({
|
||||||
method: "GET",
|
method: "GET",
|
||||||
path: "/sync",
|
path: "/sync",
|
||||||
@ -972,6 +973,7 @@ describe("MatrixClient", function () {
|
|||||||
data: SYNC_DATA,
|
data: SYNC_DATA,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const isSyncingPromise = new Promise((resolve) => {
|
||||||
client.on(ClientEvent.Sync, function syncListener(state) {
|
client.on(ClientEvent.Sync, function syncListener(state) {
|
||||||
if (state === "ERROR" && httpLookups.length > 0) {
|
if (state === "ERROR" && httpLookups.length > 0) {
|
||||||
expect(httpLookups.length).toEqual(1);
|
expect(httpLookups.length).toEqual(1);
|
||||||
@ -981,13 +983,15 @@ describe("MatrixClient", function () {
|
|||||||
jest.advanceTimersByTime(10000);
|
jest.advanceTimersByTime(10000);
|
||||||
} else if (state === "SYNCING" && httpLookups.length === 0) {
|
} else if (state === "SYNCING" && httpLookups.length === 0) {
|
||||||
client.removeListener(ClientEvent.Sync, syncListener);
|
client.removeListener(ClientEvent.Sync, syncListener);
|
||||||
done();
|
resolve(null);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
client.startClient();
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await isSyncingPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should work on /pushrules", function (done) {
|
it("should work on /pushrules", async () => {
|
||||||
httpLookups = [];
|
httpLookups = [];
|
||||||
httpLookups.push({
|
httpLookups.push({
|
||||||
method: "GET",
|
method: "GET",
|
||||||
@ -998,6 +1002,7 @@ describe("MatrixClient", function () {
|
|||||||
httpLookups.push(FILTER_RESPONSE);
|
httpLookups.push(FILTER_RESPONSE);
|
||||||
httpLookups.push(SYNC_RESPONSE);
|
httpLookups.push(SYNC_RESPONSE);
|
||||||
|
|
||||||
|
const wasPreparedPromise = new Promise((resolve) => {
|
||||||
client.on(ClientEvent.Sync, function syncListener(state) {
|
client.on(ClientEvent.Sync, function syncListener(state) {
|
||||||
if (state === "ERROR" && httpLookups.length > 0) {
|
if (state === "ERROR" && httpLookups.length > 0) {
|
||||||
expect(httpLookups.length).toEqual(3);
|
expect(httpLookups.length).toEqual(3);
|
||||||
@ -1005,13 +1010,15 @@ describe("MatrixClient", function () {
|
|||||||
jest.advanceTimersByTime(1);
|
jest.advanceTimersByTime(1);
|
||||||
} else if (state === "PREPARED" && httpLookups.length === 0) {
|
} else if (state === "PREPARED" && httpLookups.length === 0) {
|
||||||
client.removeListener(ClientEvent.Sync, syncListener);
|
client.removeListener(ClientEvent.Sync, syncListener);
|
||||||
done();
|
resolve(null);
|
||||||
} else {
|
} else {
|
||||||
// unexpected state transition!
|
// unexpected state transition!
|
||||||
expect(state).toEqual(null);
|
expect(state).toEqual(null);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
client.startClient();
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await wasPreparedPromise;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -1035,14 +1042,17 @@ describe("MatrixClient", function () {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
it("should transition null -> PREPARED after the first /sync", function (done) {
|
it("should transition null -> PREPARED after the first /sync", async () => {
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
expectedStates.push(["PREPARED", null]);
|
expectedStates.push(["PREPARED", null]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should transition null -> ERROR after a failed /filter", function (done) {
|
it("should transition null -> ERROR after a failed /filter", async () => {
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
httpLookups = [];
|
httpLookups = [];
|
||||||
httpLookups.push(PUSH_RULES_RESPONSE);
|
httpLookups.push(PUSH_RULES_RESPONSE);
|
||||||
@ -1052,14 +1062,17 @@ describe("MatrixClient", function () {
|
|||||||
error: { errcode: "NOPE_NOPE_NOPE" },
|
error: { errcode: "NOPE_NOPE_NOPE" },
|
||||||
});
|
});
|
||||||
expectedStates.push(["ERROR", null]);
|
expectedStates.push(["ERROR", null]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
// Disabled because now `startClient` makes a legit call to `/versions`
|
// Disabled because now `startClient` makes a legit call to `/versions`
|
||||||
// And those tests are really unhappy about it... Not possible to figure
|
// And those tests are really unhappy about it... Not possible to figure
|
||||||
// out what a good resolution would look like
|
// out what a good resolution would look like
|
||||||
xit("should transition ERROR -> CATCHUP after /sync if prev failed", function (done) {
|
it.skip("should transition ERROR -> CATCHUP after /sync if prev failed", async () => {
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
acceptKeepalives = false;
|
acceptKeepalives = false;
|
||||||
httpLookups = [];
|
httpLookups = [];
|
||||||
@ -1089,19 +1102,25 @@ describe("MatrixClient", function () {
|
|||||||
expectedStates.push(["RECONNECTING", null]);
|
expectedStates.push(["RECONNECTING", null]);
|
||||||
expectedStates.push(["ERROR", "RECONNECTING"]);
|
expectedStates.push(["ERROR", "RECONNECTING"]);
|
||||||
expectedStates.push(["CATCHUP", "ERROR"]);
|
expectedStates.push(["CATCHUP", "ERROR"]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should transition PREPARED -> SYNCING after /sync", function (done) {
|
it("should transition PREPARED -> SYNCING after /sync", async () => {
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
expectedStates.push(["PREPARED", null]);
|
expectedStates.push(["PREPARED", null]);
|
||||||
expectedStates.push(["SYNCING", "PREPARED"]);
|
expectedStates.push(["SYNCING", "PREPARED"]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
xit("should transition SYNCING -> ERROR after a failed /sync", function (done) {
|
it.skip("should transition SYNCING -> ERROR after a failed /sync", async () => {
|
||||||
acceptKeepalives = false;
|
acceptKeepalives = false;
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
httpLookups.push({
|
httpLookups.push({
|
||||||
@ -1119,11 +1138,14 @@ describe("MatrixClient", function () {
|
|||||||
expectedStates.push(["SYNCING", "PREPARED"]);
|
expectedStates.push(["SYNCING", "PREPARED"]);
|
||||||
expectedStates.push(["RECONNECTING", "SYNCING"]);
|
expectedStates.push(["RECONNECTING", "SYNCING"]);
|
||||||
expectedStates.push(["ERROR", "RECONNECTING"]);
|
expectedStates.push(["ERROR", "RECONNECTING"]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
xit("should transition ERROR -> SYNCING after /sync if prev failed", function (done) {
|
it.skip("should transition ERROR -> SYNCING after /sync if prev failed", async () => {
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
httpLookups.push({
|
httpLookups.push({
|
||||||
method: "GET",
|
method: "GET",
|
||||||
@ -1135,11 +1157,14 @@ describe("MatrixClient", function () {
|
|||||||
expectedStates.push(["PREPARED", null]);
|
expectedStates.push(["PREPARED", null]);
|
||||||
expectedStates.push(["SYNCING", "PREPARED"]);
|
expectedStates.push(["SYNCING", "PREPARED"]);
|
||||||
expectedStates.push(["ERROR", "SYNCING"]);
|
expectedStates.push(["ERROR", "SYNCING"]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should transition SYNCING -> SYNCING on subsequent /sync successes", function (done) {
|
it("should transition SYNCING -> SYNCING on subsequent /sync successes", async () => {
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
httpLookups.push(SYNC_RESPONSE);
|
httpLookups.push(SYNC_RESPONSE);
|
||||||
httpLookups.push(SYNC_RESPONSE);
|
httpLookups.push(SYNC_RESPONSE);
|
||||||
@ -1147,11 +1172,14 @@ describe("MatrixClient", function () {
|
|||||||
expectedStates.push(["PREPARED", null]);
|
expectedStates.push(["PREPARED", null]);
|
||||||
expectedStates.push(["SYNCING", "PREPARED"]);
|
expectedStates.push(["SYNCING", "PREPARED"]);
|
||||||
expectedStates.push(["SYNCING", "SYNCING"]);
|
expectedStates.push(["SYNCING", "SYNCING"]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
xit("should transition ERROR -> ERROR if keepalive keeps failing", function (done) {
|
it.skip("should transition ERROR -> ERROR if keepalive keeps failing", async () => {
|
||||||
acceptKeepalives = false;
|
acceptKeepalives = false;
|
||||||
const expectedStates: [string, string | null][] = [];
|
const expectedStates: [string, string | null][] = [];
|
||||||
httpLookups.push({
|
httpLookups.push({
|
||||||
@ -1175,8 +1203,11 @@ describe("MatrixClient", function () {
|
|||||||
expectedStates.push(["RECONNECTING", "SYNCING"]);
|
expectedStates.push(["RECONNECTING", "SYNCING"]);
|
||||||
expectedStates.push(["ERROR", "RECONNECTING"]);
|
expectedStates.push(["ERROR", "RECONNECTING"]);
|
||||||
expectedStates.push(["ERROR", "ERROR"]);
|
expectedStates.push(["ERROR", "ERROR"]);
|
||||||
client.on(ClientEvent.Sync, syncChecker(expectedStates, done));
|
const didSyncPromise = new Promise((resolve) => {
|
||||||
client.startClient();
|
client.on(ClientEvent.Sync, syncChecker(expectedStates, resolve));
|
||||||
|
});
|
||||||
|
await client.startClient();
|
||||||
|
await didSyncPromise;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -1214,7 +1245,7 @@ describe("MatrixClient", function () {
|
|||||||
expect(httpLookups.length).toBe(0);
|
expect(httpLookups.length).toBe(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
xit("should be able to peek into a room using peekInRoom", function (done) {});
|
it.skip("should be able to peek into a room using peekInRoom", function () {});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("getPresence", function () {
|
describe("getPresence", function () {
|
||||||
@ -1334,7 +1365,7 @@ describe("MatrixClient", function () {
|
|||||||
client.redactEvent(roomId, eventId, txnId, {
|
client.redactEvent(roomId, eventId, txnId, {
|
||||||
with_relations: [RelationType.Reference],
|
with_relations: [RelationType.Reference],
|
||||||
});
|
});
|
||||||
}).toThrowError(
|
}).toThrow(
|
||||||
new Error(
|
new Error(
|
||||||
"Server does not support relation based redactions " +
|
"Server does not support relation based redactions " +
|
||||||
`roomId ${roomId} eventId ${eventId} txnId: ${txnId} threadId null`,
|
`roomId ${roomId} eventId ${eventId} txnId: ${txnId} threadId null`,
|
||||||
@ -2410,31 +2441,6 @@ describe("MatrixClient", function () {
|
|||||||
expect(rooms).toContain(room1);
|
expect(rooms).toContain(room1);
|
||||||
expect(rooms).toContain(room2);
|
expect(rooms).toContain(room2);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("Ignores m.predecessor if we don't ask to use it", () => {
|
|
||||||
// Given 6 rooms, 2 of which have been replaced, and 2 of which WERE
|
|
||||||
// replaced by create events, but are now NOT replaced, because an
|
|
||||||
// m.predecessor event has changed the room's predecessor.
|
|
||||||
const {
|
|
||||||
room1,
|
|
||||||
room2,
|
|
||||||
replacedByCreate1,
|
|
||||||
replacedByCreate2,
|
|
||||||
replacedByDynamicPredecessor1,
|
|
||||||
replacedByDynamicPredecessor2,
|
|
||||||
} = setUpReplacedRooms();
|
|
||||||
|
|
||||||
// When we ask for the visible rooms
|
|
||||||
const rooms = client.getVisibleRooms(); // Don't supply msc3946ProcessDynamicPredecessor
|
|
||||||
|
|
||||||
// Then we only get the ones that have not been replaced
|
|
||||||
expect(rooms).not.toContain(replacedByCreate1);
|
|
||||||
expect(rooms).not.toContain(replacedByCreate2);
|
|
||||||
expect(rooms).toContain(replacedByDynamicPredecessor1);
|
|
||||||
expect(rooms).toContain(replacedByDynamicPredecessor2);
|
|
||||||
expect(rooms).toContain(room1);
|
|
||||||
expect(rooms).toContain(room2);
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("getRoomUpgradeHistory", () => {
|
describe("getRoomUpgradeHistory", () => {
|
||||||
@ -2619,7 +2625,7 @@ describe("MatrixClient", function () {
|
|||||||
expect(history.map((room) => room.roomId)).toEqual([room1.roomId]);
|
expect(history.map((room) => room.roomId)).toEqual([room1.roomId]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("Without verify links, includes predecessors that don't point forwards", () => {
|
it("Without verify links, includes successors that don't point backwards", () => {
|
||||||
// Given predecessors point forwards with tombstones, but
|
// Given predecessors point forwards with tombstones, but
|
||||||
// successors do not point back with create events.
|
// successors do not point back with create events.
|
||||||
const [room1, room2, room3, room4] = createRoomHistory(false, true);
|
const [room1, room2, room3, room4] = createRoomHistory(false, true);
|
||||||
|
@ -80,7 +80,7 @@ describe("Poll", () => {
|
|||||||
const pollStartEvent = new MatrixEvent(
|
const pollStartEvent = new MatrixEvent(
|
||||||
PollStartEvent.from("What?", ["a", "b"], M_POLL_KIND_DISCLOSED.name).serialize(),
|
PollStartEvent.from("What?", ["a", "b"], M_POLL_KIND_DISCLOSED.name).serialize(),
|
||||||
);
|
);
|
||||||
expect(() => new Poll(pollStartEvent, mockClient, room)).toThrowError("Invalid poll start event.");
|
expect(() => new Poll(pollStartEvent, mockClient, room)).toThrow("Invalid poll start event.");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("throws when poll start has no event id", () => {
|
it("throws when poll start has no event id", () => {
|
||||||
@ -88,7 +88,7 @@ describe("Poll", () => {
|
|||||||
...PollStartEvent.from("What?", ["a", "b"], M_POLL_KIND_DISCLOSED.name).serialize(),
|
...PollStartEvent.from("What?", ["a", "b"], M_POLL_KIND_DISCLOSED.name).serialize(),
|
||||||
room_id: roomId,
|
room_id: roomId,
|
||||||
});
|
});
|
||||||
expect(() => new Poll(pollStartEvent, mockClient, room)).toThrowError("Invalid poll start event.");
|
expect(() => new Poll(pollStartEvent, mockClient, room)).toThrow("Invalid poll start event.");
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("fetching responses", () => {
|
describe("fetching responses", () => {
|
||||||
@ -292,33 +292,6 @@ describe("Poll", () => {
|
|||||||
expect(maySendRedactionForEventSpy).toHaveBeenCalledWith(basePollStartEvent, "@charlie:server.org");
|
expect(maySendRedactionForEventSpy).toHaveBeenCalledWith(basePollStartEvent, "@charlie:server.org");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("does not set poll end event when an earlier end event already exists", async () => {
|
|
||||||
const earlierPollEndEvent = makeRelatedEvent(
|
|
||||||
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
|
||||||
now,
|
|
||||||
);
|
|
||||||
const laterPollEndEvent = makeRelatedEvent(
|
|
||||||
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
|
||||||
now + 2000,
|
|
||||||
);
|
|
||||||
|
|
||||||
const poll = new Poll(basePollStartEvent, mockClient, room);
|
|
||||||
await poll.getResponses();
|
|
||||||
|
|
||||||
poll.onNewRelation(earlierPollEndEvent);
|
|
||||||
|
|
||||||
// first end event set correctly
|
|
||||||
expect(poll.isEnded).toBeTruthy();
|
|
||||||
|
|
||||||
// reset spy count
|
|
||||||
jest.spyOn(poll, "emit").mockClear();
|
|
||||||
|
|
||||||
poll.onNewRelation(laterPollEndEvent);
|
|
||||||
// didn't set new end event, didn't refilter responses
|
|
||||||
expect(poll.emit).not.toHaveBeenCalled();
|
|
||||||
expect(poll.isEnded).toBeTruthy();
|
|
||||||
});
|
|
||||||
|
|
||||||
it("replaces poll end event and refilters when an older end event already exists", async () => {
|
it("replaces poll end event and refilters when an older end event already exists", async () => {
|
||||||
const earlierPollEndEvent = makeRelatedEvent(
|
const earlierPollEndEvent = makeRelatedEvent(
|
||||||
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
||||||
@ -356,25 +329,6 @@ describe("Poll", () => {
|
|||||||
expect(responses.getRelations()).toEqual([responseEventAtEnd, responseEventBeforeEnd]);
|
expect(responses.getRelations()).toEqual([responseEventAtEnd, responseEventBeforeEnd]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("does not set poll end event when sent by invalid user", async () => {
|
|
||||||
maySendRedactionForEventSpy.mockReturnValue(false);
|
|
||||||
const stablePollEndEvent = makeRelatedEvent({ type: M_POLL_END.stable!, sender: "@charlie:server.org" });
|
|
||||||
const responseEventAfterEnd = makeRelatedEvent({ type: M_POLL_RESPONSE.name }, now + 1000);
|
|
||||||
mockClient.relations.mockResolvedValue({
|
|
||||||
events: [responseEventAfterEnd],
|
|
||||||
});
|
|
||||||
const poll = new Poll(basePollStartEvent, mockClient, room);
|
|
||||||
await poll.getResponses();
|
|
||||||
jest.spyOn(poll, "emit");
|
|
||||||
|
|
||||||
poll.onNewRelation(stablePollEndEvent);
|
|
||||||
|
|
||||||
// didn't end, didn't refilter responses
|
|
||||||
expect(poll.emit).not.toHaveBeenCalled();
|
|
||||||
expect(poll.isEnded).toBeFalsy();
|
|
||||||
expect(maySendRedactionForEventSpy).toHaveBeenCalledWith(basePollStartEvent, "@charlie:server.org");
|
|
||||||
});
|
|
||||||
|
|
||||||
it("does not set poll end event when an earlier end event already exists", async () => {
|
it("does not set poll end event when an earlier end event already exists", async () => {
|
||||||
const earlierPollEndEvent = makeRelatedEvent(
|
const earlierPollEndEvent = makeRelatedEvent(
|
||||||
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
||||||
@ -402,43 +356,6 @@ describe("Poll", () => {
|
|||||||
expect(poll.isEnded).toBeTruthy();
|
expect(poll.isEnded).toBeTruthy();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("replaces poll end event and refilters when an older end event already exists", async () => {
|
|
||||||
const earlierPollEndEvent = makeRelatedEvent(
|
|
||||||
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
|
||||||
now,
|
|
||||||
);
|
|
||||||
const laterPollEndEvent = makeRelatedEvent(
|
|
||||||
{ type: M_POLL_END.stable!, sender: "@valid:server.org" },
|
|
||||||
now + 2000,
|
|
||||||
);
|
|
||||||
const responseEventBeforeEnd = makeRelatedEvent({ type: M_POLL_RESPONSE.name }, now - 1000);
|
|
||||||
const responseEventAtEnd = makeRelatedEvent({ type: M_POLL_RESPONSE.name }, now);
|
|
||||||
const responseEventAfterEnd = makeRelatedEvent({ type: M_POLL_RESPONSE.name }, now + 1000);
|
|
||||||
mockClient.relations.mockResolvedValue({
|
|
||||||
events: [responseEventAfterEnd, responseEventAtEnd, responseEventBeforeEnd, laterPollEndEvent],
|
|
||||||
});
|
|
||||||
|
|
||||||
const poll = new Poll(basePollStartEvent, mockClient, room);
|
|
||||||
const responses = await poll.getResponses();
|
|
||||||
|
|
||||||
// all responses have a timestamp < laterPollEndEvent
|
|
||||||
expect(responses.getRelations().length).toEqual(3);
|
|
||||||
// first end event set correctly
|
|
||||||
expect(poll.isEnded).toBeTruthy();
|
|
||||||
|
|
||||||
// reset spy count
|
|
||||||
jest.spyOn(poll, "emit").mockClear();
|
|
||||||
|
|
||||||
// add a valid end event with earlier timestamp
|
|
||||||
poll.onNewRelation(earlierPollEndEvent);
|
|
||||||
|
|
||||||
// emitted new end event
|
|
||||||
expect(poll.emit).toHaveBeenCalledWith(PollEvent.End);
|
|
||||||
// filtered responses and emitted
|
|
||||||
expect(poll.emit).toHaveBeenCalledWith(PollEvent.Responses, responses);
|
|
||||||
expect(responses.getRelations()).toEqual([responseEventAtEnd, responseEventBeforeEnd]);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("sets poll end event and refilters responses based on timestamp", async () => {
|
it("sets poll end event and refilters responses based on timestamp", async () => {
|
||||||
const stablePollEndEvent = makeRelatedEvent({ type: M_POLL_END.stable!, sender: userId });
|
const stablePollEndEvent = makeRelatedEvent({ type: M_POLL_END.stable!, sender: userId });
|
||||||
const responseEventBeforeEnd = makeRelatedEvent({ type: M_POLL_RESPONSE.name }, now - 1000);
|
const responseEventBeforeEnd = makeRelatedEvent({ type: M_POLL_RESPONSE.name }, now - 1000);
|
||||||
|
@ -159,7 +159,7 @@ describe("fixNotificationCountOnDecryption", () => {
|
|||||||
expect(room.getThreadUnreadNotificationCount(THREAD_ID, NotificationCountType.Highlight)).toBe(1);
|
expect(room.getThreadUnreadNotificationCount(THREAD_ID, NotificationCountType.Highlight)).toBe(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("does not change the room count when there's no unread count", () => {
|
it("does not change the thread count when there's no unread count", () => {
|
||||||
room.setThreadUnreadNotificationCount(THREAD_ID, NotificationCountType.Total, 0);
|
room.setThreadUnreadNotificationCount(THREAD_ID, NotificationCountType.Total, 0);
|
||||||
room.setThreadUnreadNotificationCount(THREAD_ID, NotificationCountType.Highlight, 0);
|
room.setThreadUnreadNotificationCount(THREAD_ID, NotificationCountType.Highlight, 0);
|
||||||
|
|
||||||
|
@ -146,7 +146,7 @@ describe("ECDHv1", function () {
|
|||||||
|
|
||||||
// send a message without encryption
|
// send a message without encryption
|
||||||
await aliceTransport.send({ iv: "dummy", ciphertext: "dummy" });
|
await aliceTransport.send({ iv: "dummy", ciphertext: "dummy" });
|
||||||
expect(bob.receive()).rejects.toThrowError();
|
expect(bob.receive()).rejects.toThrow();
|
||||||
|
|
||||||
await alice.cancel(RendezvousFailureReason.Unknown);
|
await alice.cancel(RendezvousFailureReason.Unknown);
|
||||||
await bob.cancel(RendezvousFailureReason.Unknown);
|
await bob.cancel(RendezvousFailureReason.Unknown);
|
||||||
@ -164,7 +164,7 @@ describe("ECDHv1", function () {
|
|||||||
|
|
||||||
await bobTransport.send({ iv: "dummy", ciphertext: "dummy" });
|
await bobTransport.send({ iv: "dummy", ciphertext: "dummy" });
|
||||||
|
|
||||||
expect(alice.receive()).rejects.toThrowError();
|
expect(alice.receive()).rejects.toThrow();
|
||||||
|
|
||||||
await alice.cancel(RendezvousFailureReason.Unknown);
|
await alice.cancel(RendezvousFailureReason.Unknown);
|
||||||
});
|
});
|
||||||
|
@ -220,7 +220,7 @@ describe("Rendezvous", function () {
|
|||||||
await bobStartPromise;
|
await bobStartPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
it("new device declines protocol", async function () {
|
it("new device declines protocol with outcome unsupported", async function () {
|
||||||
const aliceTransport = makeTransport("Alice", "https://test.rz/123456");
|
const aliceTransport = makeTransport("Alice", "https://test.rz/123456");
|
||||||
const bobTransport = makeTransport("Bob", "https://test.rz/999999");
|
const bobTransport = makeTransport("Bob", "https://test.rz/999999");
|
||||||
transports.push(aliceTransport, bobTransport);
|
transports.push(aliceTransport, bobTransport);
|
||||||
@ -278,7 +278,7 @@ describe("Rendezvous", function () {
|
|||||||
expect(aliceOnFailure).toHaveBeenCalledWith(RendezvousFailureReason.UnsupportedAlgorithm);
|
expect(aliceOnFailure).toHaveBeenCalledWith(RendezvousFailureReason.UnsupportedAlgorithm);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("new device declines protocol", async function () {
|
it("new device requests an invalid protocol", async function () {
|
||||||
const aliceTransport = makeTransport("Alice", "https://test.rz/123456");
|
const aliceTransport = makeTransport("Alice", "https://test.rz/123456");
|
||||||
const bobTransport = makeTransport("Bob", "https://test.rz/999999");
|
const bobTransport = makeTransport("Bob", "https://test.rz/999999");
|
||||||
transports.push(aliceTransport, bobTransport);
|
transports.push(aliceTransport, bobTransport);
|
||||||
@ -570,7 +570,7 @@ describe("Rendezvous", function () {
|
|||||||
|
|
||||||
it("device not online within timeout", async function () {
|
it("device not online within timeout", async function () {
|
||||||
const { aliceRz } = await completeLogin({});
|
const { aliceRz } = await completeLogin({});
|
||||||
expect(aliceRz.verifyNewDeviceOnExistingDevice(1000)).rejects.toThrowError();
|
expect(aliceRz.verifyNewDeviceOnExistingDevice(1000)).rejects.toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("device appears online within timeout", async function () {
|
it("device appears online within timeout", async function () {
|
||||||
@ -594,7 +594,7 @@ describe("Rendezvous", function () {
|
|||||||
getFingerprint: () => "bbbb",
|
getFingerprint: () => "bbbb",
|
||||||
};
|
};
|
||||||
}, 1500);
|
}, 1500);
|
||||||
expect(aliceRz.verifyNewDeviceOnExistingDevice(1000)).rejects.toThrowError();
|
expect(aliceRz.verifyNewDeviceOnExistingDevice(1000)).rejects.toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("mismatched device key", async function () {
|
it("mismatched device key", async function () {
|
||||||
@ -603,6 +603,6 @@ describe("Rendezvous", function () {
|
|||||||
getFingerprint: () => "XXXX",
|
getFingerprint: () => "XXXX",
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
expect(aliceRz.verifyNewDeviceOnExistingDevice(1000)).rejects.toThrowError(/different key/);
|
expect(aliceRz.verifyNewDeviceOnExistingDevice(1000)).rejects.toThrow(/different key/);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -98,7 +98,7 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
it("should throw an error when no server available", function () {
|
it("should throw an error when no server available", function () {
|
||||||
const client = makeMockClient({ userId: "@alice:example.com", deviceId: "DEVICEID", msc3886Enabled: false });
|
const client = makeMockClient({ userId: "@alice:example.com", deviceId: "DEVICEID", msc3886Enabled: false });
|
||||||
const simpleHttpTransport = new MSC3886SimpleHttpRendezvousTransport({ client, fetchFn });
|
const simpleHttpTransport = new MSC3886SimpleHttpRendezvousTransport({ client, fetchFn });
|
||||||
expect(simpleHttpTransport.send({})).rejects.toThrowError("Invalid rendezvous URI");
|
expect(simpleHttpTransport.send({})).rejects.toThrow("Invalid rendezvous URI");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("POST to fallback server", async function () {
|
it("POST to fallback server", async function () {
|
||||||
@ -130,7 +130,7 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
fetchFn,
|
fetchFn,
|
||||||
});
|
});
|
||||||
const prom = simpleHttpTransport.send({});
|
const prom = simpleHttpTransport.send({});
|
||||||
expect(prom).rejects.toThrowError();
|
expect(prom).rejects.toThrow();
|
||||||
httpBackend.when("POST", "https://fallbackserver/rz").response = {
|
httpBackend.when("POST", "https://fallbackserver/rz").response = {
|
||||||
body: null,
|
body: null,
|
||||||
response: {
|
response: {
|
||||||
@ -163,15 +163,6 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("POST with relative path response including parent", async function () {
|
|
||||||
await postAndCheckLocation(
|
|
||||||
false,
|
|
||||||
"https://fallbackserver/rz/abc",
|
|
||||||
"../xyz/123",
|
|
||||||
"https://fallbackserver/rz/xyz/123",
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
it("POST to follow 307 to other server", async function () {
|
it("POST to follow 307 to other server", async function () {
|
||||||
const client = makeMockClient({ userId: "@alice:example.com", deviceId: "DEVICEID", msc3886Enabled: false });
|
const client = makeMockClient({ userId: "@alice:example.com", deviceId: "DEVICEID", msc3886Enabled: false });
|
||||||
const simpleHttpTransport = new MSC3886SimpleHttpRendezvousTransport({
|
const simpleHttpTransport = new MSC3886SimpleHttpRendezvousTransport({
|
||||||
@ -373,7 +364,7 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
fallbackRzServer: "https://fallbackserver/rz",
|
fallbackRzServer: "https://fallbackserver/rz",
|
||||||
fetchFn,
|
fetchFn,
|
||||||
});
|
});
|
||||||
expect(simpleHttpTransport.details()).rejects.toThrowError();
|
expect(simpleHttpTransport.details()).rejects.toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("send after cancelled", async function () {
|
it("send after cancelled", async function () {
|
||||||
@ -394,7 +385,7 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
fallbackRzServer: "https://fallbackserver/rz",
|
fallbackRzServer: "https://fallbackserver/rz",
|
||||||
fetchFn,
|
fetchFn,
|
||||||
});
|
});
|
||||||
expect(simpleHttpTransport.receive()).rejects.toThrowError();
|
expect(simpleHttpTransport.receive()).rejects.toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("404 failure callback", async function () {
|
it("404 failure callback", async function () {
|
||||||
@ -416,7 +407,7 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
await httpBackend.flush("", 1);
|
await httpBackend.flush("", 1);
|
||||||
expect(onFailure).toBeCalledWith(RendezvousFailureReason.Unknown);
|
expect(onFailure).toHaveBeenCalledWith(RendezvousFailureReason.Unknown);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("404 failure callback mapped to expired", async function () {
|
it("404 failure callback mapped to expired", async function () {
|
||||||
@ -456,7 +447,7 @@ describe("SimpleHttpRendezvousTransport", function () {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
await httpBackend.flush("");
|
await httpBackend.flush("");
|
||||||
expect(onFailure).toBeCalledWith(RendezvousFailureReason.Expired);
|
expect(onFailure).toHaveBeenCalledWith(RendezvousFailureReason.Expired);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -788,8 +788,12 @@ describe("Room", function () {
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
describe("resetLiveTimeline with timeline support enabled", resetTimelineTests.bind(null, true));
|
describe("resetLiveTimeline with timeline support enabled", () => {
|
||||||
describe("resetLiveTimeline with timeline support disabled", resetTimelineTests.bind(null, false));
|
resetTimelineTests.bind(null, true);
|
||||||
|
});
|
||||||
|
describe("resetLiveTimeline with timeline support disabled", () => {
|
||||||
|
resetTimelineTests.bind(null, false);
|
||||||
|
});
|
||||||
|
|
||||||
describe("compareEventOrdering", function () {
|
describe("compareEventOrdering", function () {
|
||||||
beforeEach(function () {
|
beforeEach(function () {
|
||||||
|
@ -150,7 +150,7 @@ describe("MatrixScheduler", function () {
|
|||||||
expect(procCount).toEqual(1);
|
expect(procCount).toEqual(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should treat each queue separately", function (done) {
|
it("should treat each queue separately", async () => {
|
||||||
// Queue messages A B C D.
|
// Queue messages A B C D.
|
||||||
// Bucket A&D into queue_A
|
// Bucket A&D into queue_A
|
||||||
// Bucket B&C into queue_B
|
// Bucket B&C into queue_B
|
||||||
@ -175,14 +175,16 @@ describe("MatrixScheduler", function () {
|
|||||||
|
|
||||||
const expectOrder = [eventA.getId(), eventB.getId(), eventD.getId()];
|
const expectOrder = [eventA.getId(), eventB.getId(), eventD.getId()];
|
||||||
const deferA = defer<Record<string, boolean>>();
|
const deferA = defer<Record<string, boolean>>();
|
||||||
|
const allExpectedEventsSeenInOrderPromise = new Promise((resolve) => {
|
||||||
scheduler.setProcessFunction(function (event) {
|
scheduler.setProcessFunction(function (event) {
|
||||||
const id = expectOrder.shift();
|
const id = expectOrder.shift();
|
||||||
expect(id).toEqual(event.getId());
|
expect(id).toEqual(event.getId());
|
||||||
if (expectOrder.length === 0) {
|
if (expectOrder.length === 0) {
|
||||||
done();
|
resolve(null);
|
||||||
}
|
}
|
||||||
return id === eventA.getId() ? deferA.promise : deferred.promise;
|
return id === eventA.getId() ? deferA.promise : deferred.promise;
|
||||||
});
|
});
|
||||||
|
});
|
||||||
scheduler.queueEvent(eventA);
|
scheduler.queueEvent(eventA);
|
||||||
scheduler.queueEvent(eventB);
|
scheduler.queueEvent(eventB);
|
||||||
scheduler.queueEvent(eventC);
|
scheduler.queueEvent(eventC);
|
||||||
@ -193,6 +195,7 @@ describe("MatrixScheduler", function () {
|
|||||||
deferA.resolve({});
|
deferA.resolve({});
|
||||||
}, 1000);
|
}, 1000);
|
||||||
jest.advanceTimersByTime(1000);
|
jest.advanceTimersByTime(1000);
|
||||||
|
await allExpectedEventsSeenInOrderPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("queueEvent", function () {
|
describe("queueEvent", function () {
|
||||||
@ -290,7 +293,7 @@ describe("MatrixScheduler", function () {
|
|||||||
});
|
});
|
||||||
|
|
||||||
describe("setProcessFunction", function () {
|
describe("setProcessFunction", function () {
|
||||||
it("should call the processFn if there are queued events", function () {
|
it("should call the processFn if there are queued events", async () => {
|
||||||
queueFn = function () {
|
queueFn = function () {
|
||||||
return "yep";
|
return "yep";
|
||||||
};
|
};
|
||||||
@ -303,10 +306,9 @@ describe("MatrixScheduler", function () {
|
|||||||
});
|
});
|
||||||
// as queueing doesn't start processing synchronously anymore (see commit bbdb5ac)
|
// as queueing doesn't start processing synchronously anymore (see commit bbdb5ac)
|
||||||
// wait just long enough before it does
|
// wait just long enough before it does
|
||||||
Promise.resolve().then(() => {
|
await Promise.resolve();
|
||||||
expect(procCount).toEqual(1);
|
expect(procCount).toEqual(1);
|
||||||
});
|
});
|
||||||
});
|
|
||||||
|
|
||||||
it("should not call the processFn if there are no queued events", function () {
|
it("should not call the processFn if there are no queued events", function () {
|
||||||
queueFn = function () {
|
queueFn = function () {
|
||||||
|
@ -145,9 +145,11 @@ describe("utils", function () {
|
|||||||
describe("deepCompare", function () {
|
describe("deepCompare", function () {
|
||||||
const assert = {
|
const assert = {
|
||||||
isTrue: function (x: any) {
|
isTrue: function (x: any) {
|
||||||
|
// eslint-disable-next-line jest/no-standalone-expect
|
||||||
expect(x).toBe(true);
|
expect(x).toBe(true);
|
||||||
},
|
},
|
||||||
isFalse: function (x: any) {
|
isFalse: function (x: any) {
|
||||||
|
// eslint-disable-next-line jest/no-standalone-expect
|
||||||
expect(x).toBe(false);
|
expect(x).toBe(false);
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
@ -1579,7 +1579,7 @@ describe("Call", function () {
|
|||||||
hasAdvancedBy += advanceBy;
|
hasAdvancedBy += advanceBy;
|
||||||
|
|
||||||
expect(lengthChangedListener).toHaveBeenCalledTimes(hasAdvancedBy);
|
expect(lengthChangedListener).toHaveBeenCalledTimes(hasAdvancedBy);
|
||||||
expect(lengthChangedListener).toBeCalledWith(hasAdvancedBy);
|
expect(lengthChangedListener).toHaveBeenCalledWith(hasAdvancedBy);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -147,7 +147,7 @@ describe("Group Call", function () {
|
|||||||
async (state: GroupCallState) => {
|
async (state: GroupCallState) => {
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
groupCall.state = state;
|
groupCall.state = state;
|
||||||
await expect(groupCall.initLocalCallFeed()).rejects.toThrowError();
|
await expect(groupCall.initLocalCallFeed()).rejects.toThrow();
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -389,7 +389,7 @@ describe("Group Call", function () {
|
|||||||
jest.spyOn(call, "getOpponentMember").mockReturnValue({ userId: undefined });
|
jest.spyOn(call, "getOpponentMember").mockReturnValue({ userId: undefined });
|
||||||
|
|
||||||
// @ts-ignore Mock
|
// @ts-ignore Mock
|
||||||
expect(() => groupCall.onCallFeedsChanged(call)).toThrowError();
|
expect(() => groupCall.onCallFeedsChanged(call)).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("usermedia feeds", () => {
|
describe("usermedia feeds", () => {
|
||||||
|
@ -401,7 +401,7 @@ describe("Media Handler", function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("stopUserMediaStream", () => {
|
describe("stopScreensharingStream", () => {
|
||||||
let stream: MediaStream;
|
let stream: MediaStream;
|
||||||
|
|
||||||
beforeEach(async () => {
|
beforeEach(async () => {
|
||||||
|
17
yarn.lock
17
yarn.lock
@ -1869,7 +1869,7 @@
|
|||||||
semver "^7.3.7"
|
semver "^7.3.7"
|
||||||
tsutils "^3.21.0"
|
tsutils "^3.21.0"
|
||||||
|
|
||||||
"@typescript-eslint/utils@5.51.0":
|
"@typescript-eslint/utils@5.51.0", "@typescript-eslint/utils@^5.10.0":
|
||||||
version "5.51.0"
|
version "5.51.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-5.51.0.tgz#074f4fabd5b12afe9c8aa6fdee881c050f8b4d47"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-5.51.0.tgz#074f4fabd5b12afe9c8aa6fdee881c050f8b4d47"
|
||||||
integrity sha512-76qs+5KWcaatmwtwsDJvBk4H76RJQBFe+Gext0EfJdC3Vd2kpY2Pf//OHHzHp84Ciw0/rYoGTDnIAr3uWhhJYw==
|
integrity sha512-76qs+5KWcaatmwtwsDJvBk4H76RJQBFe+Gext0EfJdC3Vd2kpY2Pf//OHHzHp84Ciw0/rYoGTDnIAr3uWhhJYw==
|
||||||
@ -3414,6 +3414,13 @@ eslint-plugin-import@^2.26.0:
|
|||||||
semver "^6.3.0"
|
semver "^6.3.0"
|
||||||
tsconfig-paths "^3.14.1"
|
tsconfig-paths "^3.14.1"
|
||||||
|
|
||||||
|
eslint-plugin-jest@^27.1.6:
|
||||||
|
version "27.2.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/eslint-plugin-jest/-/eslint-plugin-jest-27.2.1.tgz#b85b4adf41c682ea29f1f01c8b11ccc39b5c672c"
|
||||||
|
integrity sha512-l067Uxx7ZT8cO9NJuf+eJHvt6bqJyz2Z29wykyEdz/OtmcELQl2MQGQLX8J94O1cSJWAwUSEvCjwjA7KEK3Hmg==
|
||||||
|
dependencies:
|
||||||
|
"@typescript-eslint/utils" "^5.10.0"
|
||||||
|
|
||||||
eslint-plugin-jsdoc@^39.6.4:
|
eslint-plugin-jsdoc@^39.6.4:
|
||||||
version "39.8.0"
|
version "39.8.0"
|
||||||
resolved "https://registry.yarnpkg.com/eslint-plugin-jsdoc/-/eslint-plugin-jsdoc-39.8.0.tgz#9ca38ae31fb6e6de6268c5c041fa175fe1190469"
|
resolved "https://registry.yarnpkg.com/eslint-plugin-jsdoc/-/eslint-plugin-jsdoc-39.8.0.tgz#9ca38ae31fb6e6de6268c5c041fa175fe1190469"
|
||||||
@ -3427,10 +3434,10 @@ eslint-plugin-jsdoc@^39.6.4:
|
|||||||
semver "^7.3.8"
|
semver "^7.3.8"
|
||||||
spdx-expression-parse "^3.0.1"
|
spdx-expression-parse "^3.0.1"
|
||||||
|
|
||||||
eslint-plugin-matrix-org@^0.10.0:
|
eslint-plugin-matrix-org@^1.0.0:
|
||||||
version "0.10.0"
|
version "1.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/eslint-plugin-matrix-org/-/eslint-plugin-matrix-org-0.10.0.tgz#8d0998641a4d276343cae2abf253a01bb4d4cc60"
|
resolved "https://registry.yarnpkg.com/eslint-plugin-matrix-org/-/eslint-plugin-matrix-org-1.0.0.tgz#cead71391e2a36d63cb8f8018a38305ecf81b4b8"
|
||||||
integrity sha512-L7ail0x1yUlF006kn4mHc+OT8/aYZI++i852YXPHxCbM1EY7jeg/fYAQ8tCx5+x08LyqXeS7inAVSL784m0C6Q==
|
integrity sha512-JSjw+hswEcFR+N4N2JXZttK65cK6huykZKkbnwcITxPTelsaOfZ8qXG0Az9BfmVADaLgY3MGmHK1YYKbykUfBQ==
|
||||||
|
|
||||||
eslint-plugin-tsdoc@^0.2.17:
|
eslint-plugin-tsdoc@^0.2.17:
|
||||||
version "0.2.17"
|
version "0.2.17"
|
||||||
|
Reference in New Issue
Block a user