add knock support

Fixes #123
This commit is contained in:
Henry Hiles 2026-10-21 12:32:02 -04:00
commit 427e06be3e
Signed by: Henry-Hiles
SSH key fingerprint: SHA256:VKQUdS31Q90KvX7EkKMHMBpUspcmItAh86a+v7PGiIs
2 changed files with 399 additions and 194 deletions

View file

@ -9,6 +9,7 @@ part "join_room.g.dart";
class const JoinRoomRequest({
required final String roomIdOrAlias,
final IList<String> via = const .empty(),
final String? reason,
/// Set when accepting an invite, so gomuks can mark DMs as such.
final bool fromInvite = false,

View file

@ -1,3 +1,4 @@
import "package:fast_immutable_collections/fast_immutable_collections.dart";
import "package:freezed_annotation/freezed_annotation.dart";
import "package:nexus/models/content/create.dart";
import "package:nexus/models/content/membership.dart";
@ -14,6 +15,9 @@ class const RoomSummary({
required final String roomId,
@JsonKey(name: "num_joined_members") final int? joinedMembers,
final JoinRule? joinRule,
/// Rooms whose members may join without an invite, for restricted rooms.
final IList<String> allowedRoomIds = const .empty(),
final String? name,
final Uri? avatarUrl,
final String? canonicalAlias,
@ -41,6 +45,14 @@ class const RoomSummary({
/// Whether this is an invite to a direct message.
@JsonKey(includeFromJson: false) final bool isDirect = false,
}) with _$RoomSummary {
/// Whether the user has to knock rather than join, given the rooms they've
/// joined. Restricted knock rooms can be joined directly from an allowed room.
bool mustKnock(ISet<String> joinedRooms) => switch (joinRule) {
.knock => true,
.knockRestricted => !allowedRoomIds.any(joinedRooms.contains),
_ => false,
};
/// A summary of a room the user is in, from its synced metadata.
factory RoomSummary.fromMetadata(RoomMetadata metadata) => .new(
roomId: metadata.id,