@@ -5,24 +5,26 @@ SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Com
5
5
Please see LICENSE files in the repository root for full details.
6
6
*/
7
7
8
- import type { MatrixDispatcher } from "../../../../src/dispatcher/dispatcher" ;
8
+ import { EventType , KnownMembership , MatrixEvent , Room } from "matrix-js-sdk/src/matrix" ;
9
+
9
10
import { RoomListStoreV3Class } from "../../../../src/stores/room-list-v3/RoomListStoreV3" ;
10
11
import { AsyncStoreWithClient } from "../../../../src/stores/AsyncStoreWithClient" ;
11
12
import { RecencySorter } from "../../../../src/stores/room-list-v3/skip-list/sorters/RecencySorter" ;
12
- import { stubClient } from "../../../test-utils" ;
13
+ import { mkEvent , mkMessage , stubClient , upsertRoomStateEvents } from "../../../test-utils" ;
13
14
import { getMockedRooms } from "./skip-list/getMockedRooms" ;
14
15
import { AlphabeticSorter } from "../../../../src/stores/room-list-v3/skip-list/sorters/AlphabeticSorter" ;
16
+ import dispatcher from "../../../../src/dispatcher/dispatcher" ;
17
+ import { LISTS_UPDATE_EVENT } from "../../../../src/stores/room-list/RoomListStore" ;
15
18
16
19
describe ( "RoomListStoreV3" , ( ) => {
17
20
async function getRoomListStore ( ) {
18
21
const client = stubClient ( ) ;
19
22
const rooms = getMockedRooms ( client ) ;
20
23
client . getVisibleRooms = jest . fn ( ) . mockReturnValue ( rooms ) ;
21
24
jest . spyOn ( AsyncStoreWithClient . prototype , "matrixClient" , "get" ) . mockReturnValue ( client ) ;
22
- const fakeDispatcher = { register : jest . fn ( ) } as unknown as MatrixDispatcher ;
23
- const store = new RoomListStoreV3Class ( fakeDispatcher ) ;
25
+ const store = new RoomListStoreV3Class ( dispatcher ) ;
24
26
store . start ( ) ;
25
- return { client, rooms, store } ;
27
+ return { client, rooms, store, dispatcher } ;
26
28
}
27
29
28
30
it ( "Provides an unsorted list of rooms" , async ( ) => {
@@ -50,4 +52,107 @@ describe("RoomListStoreV3", () => {
50
52
sortedRooms = new RecencySorter ( client . getSafeUserId ( ) ) . sort ( rooms ) ;
51
53
expect ( store . getSortedRooms ( ) ) . toEqual ( sortedRooms ) ;
52
54
} ) ;
55
+
56
+ describe ( "Updates" , ( ) => {
57
+ it ( "Room is re-inserted on timeline event" , async ( ) => {
58
+ const { store, rooms, dispatcher } = await getRoomListStore ( ) ;
59
+
60
+ // Let's pretend like a new timeline event came on the room in 37th index.
61
+ const room = rooms [ 37 ] ;
62
+ const event = mkMessage ( { room : room . roomId , user : `@foo${ 3 } :matrix.org` , ts : 1000 , event : true } ) ;
63
+ room . timeline . push ( event ) ;
64
+
65
+ const payload = {
66
+ action : "MatrixActions.Room.timeline" ,
67
+ event,
68
+ isLiveEvent : true ,
69
+ isLiveUnfilteredRoomTimelineEvent : true ,
70
+ room,
71
+ } ;
72
+
73
+ const fn = jest . fn ( ) ;
74
+ store . on ( LISTS_UPDATE_EVENT , fn ) ;
75
+ dispatcher . dispatch ( payload , true ) ;
76
+
77
+ expect ( fn ) . toHaveBeenCalled ( ) ;
78
+ expect ( store . getSortedRooms ( ) [ 0 ] . roomId ) . toEqual ( room . roomId ) ;
79
+ } ) ;
80
+
81
+ it ( "Predecessor room is removed on room upgrade" , async ( ) => {
82
+ const { store, rooms, client, dispatcher } = await getRoomListStore ( ) ;
83
+ // Let's say that !foo32:matrix.org is being upgraded
84
+ const oldRoom = rooms [ 32 ] ;
85
+ // Create a new room with a predecessor event that points to oldRoom
86
+ const newRoom = new Room ( "!foonew:matrix.org" , client , client . getSafeUserId ( ) , { } ) ;
87
+ const createWithPredecessor = new MatrixEvent ( {
88
+ type : EventType . RoomCreate ,
89
+ sender : "@foo:foo.org" ,
90
+ room_id : newRoom . roomId ,
91
+ content : {
92
+ predecessor : { room_id : oldRoom . roomId , event_id : "tombstone_event_id" } ,
93
+ } ,
94
+ event_id : "$create" ,
95
+ state_key : "" ,
96
+ } ) ;
97
+ upsertRoomStateEvents ( newRoom , [ createWithPredecessor ] ) ;
98
+
99
+ const fn = jest . fn ( ) ;
100
+ store . on ( LISTS_UPDATE_EVENT , fn ) ;
101
+ dispatcher . dispatch (
102
+ {
103
+ action : "MatrixActions.Room.myMembership" ,
104
+ oldMembership : KnownMembership . Invite ,
105
+ membership : KnownMembership . Join ,
106
+ room : newRoom ,
107
+ } ,
108
+ true ,
109
+ ) ;
110
+
111
+ expect ( fn ) . toHaveBeenCalled ( ) ;
112
+ const roomIds = store . getSortedRooms ( ) . map ( ( r ) => r . roomId ) ;
113
+ expect ( roomIds ) . not . toContain ( oldRoom . roomId ) ;
114
+ expect ( roomIds ) . toContain ( newRoom . roomId ) ;
115
+ } ) ;
116
+
117
+ it ( "Rooms are inserted on m.direct event" , async ( ) => {
118
+ const { store, dispatcher } = await getRoomListStore ( ) ;
119
+
120
+ // Let's create a m.direct event that we can dispatch
121
+ const content = {
122
+ "@bar1:matrix.org" : [ "!newroom1:matrix.org" , "!newroom2:matrix.org" ] ,
123
+ "@bar2:matrix.org" : [ "!newroom3:matrix.org" , "!newroom4:matrix.org" ] ,
124
+ "@bar3:matrix.org" : [ "!newroom5:matrix.org" ] ,
125
+ } ;
126
+ const event = mkEvent ( {
127
+ event : true ,
128
+ content,
129
+ user : "@foo:matrix.org" ,
130
+ type : EventType . Direct ,
131
+ } ) ;
132
+
133
+ const fn = jest . fn ( ) ;
134
+ store . on ( LISTS_UPDATE_EVENT , fn ) ;
135
+ dispatcher . dispatch (
136
+ {
137
+ action : "MatrixActions.accountData" ,
138
+ event_type : EventType . Direct ,
139
+ event,
140
+ } ,
141
+ true ,
142
+ ) ;
143
+
144
+ // Each of these rooms should now appear in the store
145
+ // We don't need to mock the rooms themselves since our mocked
146
+ // client will create the rooms on getRoom() call.
147
+ expect ( fn ) . toHaveBeenCalledTimes ( 5 ) ;
148
+ const roomIds = store . getSortedRooms ( ) . map ( ( r ) => r . roomId ) ;
149
+ [
150
+ "!newroom1:matrix.org" ,
151
+ "!newroom2:matrix.org" ,
152
+ "!newroom3:matrix.org" ,
153
+ "!newroom4:matrix.org" ,
154
+ "!newroom5:matrix.org" ,
155
+ ] . forEach ( ( id ) => expect ( roomIds ) . toContain ( id ) ) ;
156
+ } ) ;
157
+ } ) ;
53
158
} ) ;
0 commit comments