Fix corrupt thread timeline for sending events (#11260)
Events which are still in the process of being sent should *not* be included in the `EventTimeline`. Doing so means that we will attempt to render them twice, which makes react explode. Fixes https://github.com/vector-im/element-web/issues/25770
This commit is contained in:
parent
cb592dc709
commit
e959eca354
3 changed files with 26 additions and 7 deletions
|
@ -214,7 +214,12 @@ export default class ThreadView extends React.Component<IProps, IState> {
|
|||
let thread = this.props.room.getThread(eventId);
|
||||
|
||||
if (!thread) {
|
||||
thread = this.props.room.createThread(eventId, mxEv, [mxEv], true);
|
||||
const events = [];
|
||||
// if the event is still being sent, don't include it in the Thread yet - otherwise the timeline panel
|
||||
// will attempt to show it twice (once as a regular event, once as a pending event) and everything will
|
||||
// blow up
|
||||
if (mxEv.status === null) events.push(mxEv);
|
||||
thread = this.props.room.createThread(eventId, mxEv, events, true);
|
||||
}
|
||||
|
||||
this.updateThread(thread);
|
||||
|
|
|
@ -19,7 +19,7 @@ import userEvent from "@testing-library/user-event";
|
|||
import { mocked } from "jest-mock";
|
||||
import { MsgType, RelationType } from "matrix-js-sdk/src/@types/event";
|
||||
import { MatrixClient, PendingEventOrdering } from "matrix-js-sdk/src/client";
|
||||
import { MatrixEvent } from "matrix-js-sdk/src/models/event";
|
||||
import { EventStatus, MatrixEvent } from "matrix-js-sdk/src/models/event";
|
||||
import { Room } from "matrix-js-sdk/src/models/room";
|
||||
import { THREAD_RELATION_TYPE } from "matrix-js-sdk/src/models/thread";
|
||||
import React, { useState } from "react";
|
||||
|
@ -35,7 +35,7 @@ import DMRoomMap from "../../../src/utils/DMRoomMap";
|
|||
import ResizeNotifier from "../../../src/utils/ResizeNotifier";
|
||||
import { mockPlatformPeg } from "../../test-utils/platform";
|
||||
import { getRoomContext } from "../../test-utils/room";
|
||||
import { stubClient } from "../../test-utils/test-utils";
|
||||
import { mkMessage, stubClient } from "../../test-utils/test-utils";
|
||||
import { mkThread } from "../../test-utils/threads";
|
||||
|
||||
describe("ThreadView", () => {
|
||||
|
@ -135,6 +135,24 @@ describe("ThreadView", () => {
|
|||
jest.spyOn(DMRoomMap.shared(), "getUserIdForRoomId").mockReturnValue(SENDER);
|
||||
});
|
||||
|
||||
it("does not include pending root event in the timeline twice", async () => {
|
||||
rootEvent = mkMessage({
|
||||
user: mockClient.getUserId()!,
|
||||
event: true,
|
||||
room: room.roomId,
|
||||
msg: "root event message " + Math.random(),
|
||||
});
|
||||
|
||||
rootEvent.status = EventStatus.SENDING;
|
||||
rootEvent.setTxnId("1234");
|
||||
room.addPendingEvent(rootEvent, "1234");
|
||||
room.updatePendingEvent(rootEvent, EventStatus.SENT, rootEvent.getId());
|
||||
|
||||
const { container } = await getComponent();
|
||||
const tiles = container.getElementsByClassName("mx_EventTile");
|
||||
expect(tiles.length).toEqual(1);
|
||||
});
|
||||
|
||||
it("sends a message with the correct fallback", async () => {
|
||||
const { container } = await getComponent();
|
||||
|
||||
|
|
|
@ -136,10 +136,6 @@ export const mkThread = ({
|
|||
|
||||
const thread = room.createThread(rootEvent.getId()!, rootEvent, events, true);
|
||||
|
||||
events.forEach((event) => {
|
||||
thread.timeline.push(event);
|
||||
});
|
||||
|
||||
// So that we do not have to mock the thread loading
|
||||
thread.initialEventsFetched = true;
|
||||
|
||||
|
|
Loading…
Reference in a new issue