Skip to content

Commit 29d3856

Browse files
authored
Merge pull request #7424 from vector-im/feature/eric/msc3773
Implements MSC3773 (Thread Notifications)
2 parents e41b1a6 + b34468b commit 29d3856

File tree

15 files changed

+160
-37
lines changed

15 files changed

+160
-37
lines changed

changelog.d/7424.misc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Gets thread notifications from sync response

matrix-sdk-android/src/main/java/org/matrix/android/sdk/api/session/room/model/RoomSummary.kt

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,14 @@ data class RoomSummary(
9797
* Number of unread and highlighted message in this room.
9898
*/
9999
val highlightCount: Int = 0,
100+
/**
101+
* Number of threads with unread messages in this room.
102+
*/
103+
val threadNotificationCount: Int = 0,
104+
/**
105+
* Number of threads with highlighted messages in this room.
106+
*/
107+
val threadHighlightCount: Int = 0,
100108
/**
101109
* True if this room has unread messages.
102110
*/

matrix-sdk-android/src/main/java/org/matrix/android/sdk/api/session/sync/model/RoomSync.kt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,11 @@ data class RoomSync(
4747
*/
4848
@Json(name = "unread_notifications") val unreadNotifications: RoomSyncUnreadNotifications? = null,
4949

50+
/**
51+
* The count of threads with unread notifications (not the total # of notifications in all threads).
52+
*/
53+
@Json(name = "unread_thread_notifications") val unreadThreadNotifications: Map<String, RoomSyncUnreadThreadNotifications>? = null,
54+
5055
/**
5156
* The room summary.
5257
*/
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
/*
2+
* Copyright 2022 The Matrix.org Foundation C.I.C.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package org.matrix.android.sdk.api.session.sync.model
18+
19+
import com.squareup.moshi.Json
20+
import com.squareup.moshi.JsonClass
21+
22+
@JsonClass(generateAdapter = true)
23+
data class RoomSyncUnreadThreadNotifications(
24+
/**
25+
* The number of threads with unread messages that match the push notification rules.
26+
*/
27+
@Json(name = "notification_count") val notificationCount: Int? = null,
28+
29+
/**
30+
* The number of threads with highlighted unread messages (subset of notifications).
31+
*/
32+
@Json(name = "highlight_count") val highlightCount: Int? = null
33+
)

matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/RealmSessionStoreMigration.kt

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@ import org.matrix.android.sdk.internal.database.migration.MigrateSessionTo037
5757
import org.matrix.android.sdk.internal.database.migration.MigrateSessionTo038
5858
import org.matrix.android.sdk.internal.database.migration.MigrateSessionTo039
5959
import org.matrix.android.sdk.internal.database.migration.MigrateSessionTo040
60+
import org.matrix.android.sdk.internal.database.migration.MigrateSessionTo041
6061
import org.matrix.android.sdk.internal.util.Normalizer
6162
import org.matrix.android.sdk.internal.util.database.MatrixRealmMigration
6263
import javax.inject.Inject
@@ -65,7 +66,7 @@ internal class RealmSessionStoreMigration @Inject constructor(
6566
private val normalizer: Normalizer
6667
) : MatrixRealmMigration(
6768
dbName = "Session",
68-
schemaVersion = 40L,
69+
schemaVersion = 41L,
6970
) {
7071
/**
7172
* Forces all RealmSessionStoreMigration instances to be equal.
@@ -115,5 +116,6 @@ internal class RealmSessionStoreMigration @Inject constructor(
115116
if (oldVersion < 38) MigrateSessionTo038(realm).perform()
116117
if (oldVersion < 39) MigrateSessionTo039(realm).perform()
117118
if (oldVersion < 40) MigrateSessionTo040(realm).perform()
119+
if (oldVersion < 41) MigrateSessionTo041(realm).perform()
118120
}
119121
}

matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/RoomSummaryMapper.kt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,8 @@ internal class RoomSummaryMapper @Inject constructor(
6161
otherMemberIds = roomSummaryEntity.otherMemberIds.toList(),
6262
highlightCount = roomSummaryEntity.highlightCount,
6363
notificationCount = roomSummaryEntity.notificationCount,
64+
threadHighlightCount = roomSummaryEntity.threadHighlightCount,
65+
threadNotificationCount = roomSummaryEntity.threadNotificationCount,
6466
hasUnreadMessages = roomSummaryEntity.hasUnreadMessages,
6567
tags = tags,
6668
typingUsers = typingUsers,
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
/*
2+
* Copyright (c) 2022 The Matrix.org Foundation C.I.C.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package org.matrix.android.sdk.internal.database.migration
18+
19+
import io.realm.DynamicRealm
20+
import org.matrix.android.sdk.internal.database.model.RoomSummaryEntityFields
21+
import org.matrix.android.sdk.internal.util.database.RealmMigrator
22+
23+
internal class MigrateSessionTo041(realm: DynamicRealm) : RealmMigrator(realm, 41) {
24+
25+
override fun doMigrate(realm: DynamicRealm) {
26+
realm.schema.get("RoomSummaryEntity")
27+
?.addField(RoomSummaryEntityFields.THREAD_HIGHLIGHT_COUNT, Int::class.java)
28+
?.addField(RoomSummaryEntityFields.THREAD_NOTIFICATION_COUNT, Int::class.java)
29+
}
30+
}

matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/model/RoomSummaryEntity.kt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,16 @@ internal open class RoomSummaryEntity(
115115
if (value != field) field = value
116116
}
117117

118+
var threadNotificationCount: Int = 0
119+
set(value) {
120+
if (value != field) field = value
121+
}
122+
123+
var threadHighlightCount: Int = 0
124+
set(value) {
125+
if (value != field) field = value
126+
}
127+
118128
var readMarkerId: String? = null
119129
set(value) {
120130
if (value != field) field = value

matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/query/TimelineEventEntityQueries.kt

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -110,8 +110,7 @@ internal fun RealmQuery<TimelineEventEntity>.filterEvents(filters: TimelineEvent
110110
endGroup()
111111
}
112112
if (filters.filterUseless) {
113-
not()
114-
.equalTo(TimelineEventEntityFields.ROOT.IS_USELESS, true)
113+
not().equalTo(TimelineEventEntityFields.ROOT.IS_USELESS, true)
115114
}
116115
if (filters.filterEdits) {
117116
not().like(TimelineEventEntityFields.ROOT.CONTENT, TimelineEventFilter.Content.EDIT)

matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/session/filter/FilterFactory.kt

Lines changed: 6 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ internal object FilterFactory {
2828
limit = numberOfEvents,
2929
// senders = listOf(userId),
3030
// relationSenders = userId?.let { listOf(it) },
31-
relationTypes = listOf(RelationType.THREAD)
31+
relationTypes = listOf(RelationType.THREAD),
3232
)
3333
}
3434

@@ -37,7 +37,7 @@ internal object FilterFactory {
3737
limit = numberOfEvents,
3838
containsUrl = true,
3939
types = listOf(EventType.MESSAGE),
40-
lazyLoadMembers = true
40+
lazyLoadMembers = true,
4141
)
4242
}
4343

@@ -55,30 +55,23 @@ internal object FilterFactory {
5555
}
5656

5757
fun createDefaultRoomFilter(): RoomEventFilter {
58-
return RoomEventFilter(
59-
lazyLoadMembers = true
60-
)
58+
return RoomEventFilter(lazyLoadMembers = true)
6159
}
6260

6361
fun createElementRoomFilter(): RoomEventFilter {
6462
return RoomEventFilter(
65-
lazyLoadMembers = true
63+
lazyLoadMembers = true,
6664
// TODO Enable this for optimization
6765
// types = (listOfSupportedEventTypes + listOfSupportedStateEventTypes).toMutableList()
6866
)
6967
}
7068

7169
private fun createElementTimelineFilter(): RoomEventFilter? {
72-
return null // RoomEventFilter().apply {
73-
// TODO Enable this for optimization
74-
// types = listOfSupportedEventTypes.toMutableList()
75-
// }
70+
return RoomEventFilter(enableUnreadThreadNotifications = true)
7671
}
7772

7873
private fun createElementStateFilter(): RoomEventFilter {
79-
return RoomEventFilter(
80-
lazyLoadMembers = true
81-
)
74+
return RoomEventFilter(lazyLoadMembers = true)
8275
}
8376

8477
// Get only managed types by Element

0 commit comments

Comments
 (0)