add GomuksEvent model
This commit is contained in:
parent
b4d5a632dd
commit
b154b4ee2e
8 changed files with 114 additions and 93 deletions
|
|
@ -8,6 +8,7 @@ import "package:nexus/controllers/client.dart";
|
|||
import "package:nexus/models/account_data.dart";
|
||||
import "package:nexus/models/push_rules.dart";
|
||||
import "package:nexus/models/requests/update_push_rule.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
|
||||
class AccountDataController extends Notifier<AccountData> {
|
||||
@override
|
||||
|
|
@ -26,6 +27,11 @@ class AccountDataController extends Notifier<AccountData> {
|
|||
}
|
||||
});
|
||||
|
||||
void handleSync(SyncData sync) {
|
||||
if (sync.clearState) state = .new();
|
||||
update(sync.accountData);
|
||||
}
|
||||
|
||||
Future<void> setEnabledImagePacks(ImagePackRooms packs) {
|
||||
ISet<(String, String)> keysOf(ImagePackRooms rooms) => rooms.rooms.entries
|
||||
.expand((entry) => entry.value.keys.map((key) => (entry.key, key)))
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@ import "dart:io";
|
|||
import "dart:isolate";
|
||||
|
||||
import "package:collection/collection.dart";
|
||||
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||
import "package:flutter/foundation.dart";
|
||||
import "package:nexus/controllers/account_data.dart";
|
||||
import "package:nexus/controllers/accounts.dart";
|
||||
|
|
@ -22,9 +21,7 @@ import "package:nexus/controllers/typing.dart";
|
|||
import "package:nexus/helpers/extensions/gomuks_buffer.dart";
|
||||
import "package:nexus/main.dart";
|
||||
import "package:ffi/ffi.dart";
|
||||
import "package:nexus/models/event.dart";
|
||||
import "package:nexus/models/events_decrypted.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
import "package:nexus/models/gomuks_event.dart";
|
||||
import "package:nexus/src/third_party/gomuks.g.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
|
||||
|
|
@ -42,100 +39,43 @@ class GomuksListenerController extends AsyncNotifier<void> {
|
|||
int requestId,
|
||||
GomuksOwnedBuffer data,
|
||||
) {
|
||||
final type = command.cast<Utf8>().toDartString();
|
||||
try {
|
||||
final muksEventType = command.cast<Utf8>().toDartString();
|
||||
debugPrint("Handling $muksEventType...");
|
||||
final decodedMuksEvent = data.toJsonAndFree();
|
||||
|
||||
switch (muksEventType) {
|
||||
case "client_state":
|
||||
ref
|
||||
.read(ClientStateController.provider.notifier)
|
||||
.set(.fromJson(decodedMuksEvent));
|
||||
case "sync_status":
|
||||
ref
|
||||
.read(SyncStatusController.provider.notifier)
|
||||
.set(.fromJson(decodedMuksEvent));
|
||||
case "init_complete":
|
||||
debugPrint("Handling $type...");
|
||||
switch (GomuksEvent.parse(type, data.toJsonAndFree())) {
|
||||
case ClientStateEvent(:final state):
|
||||
ref.read(ClientStateController.provider.notifier).set(state);
|
||||
case SyncStatusEvent(:final status):
|
||||
ref.read(SyncStatusController.provider.notifier).set(status);
|
||||
case InitCompleteEvent():
|
||||
ref.read(InitCompleteController.provider.notifier).complete();
|
||||
case "send_complete":
|
||||
final event = Event.fromJson(decodedMuksEvent["event"]);
|
||||
case SendCompleteEvent(:final event):
|
||||
ref.read(RoomsController.provider.notifier).storeEvents([
|
||||
event,
|
||||
]);
|
||||
case TypingEvent(:final typing):
|
||||
ref.read(TypingController.provider.notifier).set(typing);
|
||||
case EventsDecryptedEvent(:final decrypted):
|
||||
ref
|
||||
.read(RoomsController.provider.notifier)
|
||||
.update(
|
||||
.new({
|
||||
event.roomId: .new(events: .new({event.rowId: event})),
|
||||
}),
|
||||
);
|
||||
case "typing":
|
||||
.handleDecrypted(decrypted);
|
||||
case SyncCompleteEvent(:final sync):
|
||||
ref.read(RoomsController.provider.notifier).handleSync(sync);
|
||||
ref
|
||||
.read(TypingController.provider.notifier)
|
||||
.set(.fromJson(decodedMuksEvent));
|
||||
case "events_decrypted":
|
||||
final decrypted = EventsDecrypted.fromJson(decodedMuksEvent);
|
||||
final metadata = ref
|
||||
.read(RoomsController.provider)[decrypted.roomId]
|
||||
?.metadata;
|
||||
|
||||
ref
|
||||
.read(RoomsController.provider.notifier)
|
||||
.update(
|
||||
.new({
|
||||
decrypted.roomId: .new(
|
||||
events: decrypted.events,
|
||||
metadata: metadata?.copyWith(
|
||||
previewEventRowID:
|
||||
decrypted.previewEventRowID ??
|
||||
metadata.previewEventRowID,
|
||||
sortingTimestamp:
|
||||
decrypted.sortingTimestamp ??
|
||||
metadata.sortingTimestamp,
|
||||
),
|
||||
),
|
||||
}),
|
||||
);
|
||||
case "sync_complete":
|
||||
final syncData = SyncData.fromJson(decodedMuksEvent);
|
||||
final roomProvider = RoomsController.provider;
|
||||
final accountDataProvider = AccountDataController.provider;
|
||||
final invitesProvider = InvitesController.provider;
|
||||
|
||||
if (syncData.clearState) {
|
||||
ref.invalidate(roomProvider);
|
||||
ref.invalidate(accountDataProvider);
|
||||
ref.invalidate(invitesProvider);
|
||||
ref.invalidate(TypingController.provider);
|
||||
}
|
||||
|
||||
ref
|
||||
.read(roomProvider.notifier)
|
||||
.update(syncData.rooms, syncData.leftRooms);
|
||||
ref
|
||||
.read(accountDataProvider.notifier)
|
||||
.update(syncData.accountData);
|
||||
ref
|
||||
.read(invitesProvider.notifier)
|
||||
.update(
|
||||
syncData.invitedRooms,
|
||||
joinedRooms: syncData.rooms.keys.toISet(),
|
||||
leftRooms: syncData.leftRooms,
|
||||
);
|
||||
|
||||
if (syncData.topLevelSpaces case final topLevelSpaces?) {
|
||||
.read(AccountDataController.provider.notifier)
|
||||
.handleSync(sync);
|
||||
ref.read(InvitesController.provider.notifier).handleSync(sync);
|
||||
ref.read(TypingController.provider.notifier).handleSync(sync);
|
||||
ref
|
||||
.read(TopLevelSpacesController.provider.notifier)
|
||||
.set(topLevelSpaces);
|
||||
}
|
||||
|
||||
if (syncData.spaceEdges case final spaceEdges?) {
|
||||
.handleSync(sync);
|
||||
ref
|
||||
.read(SpaceEdgesController.provider.notifier)
|
||||
.set(spaceEdges);
|
||||
.handleSync(sync);
|
||||
case UnknownGomuksEvent():
|
||||
debugPrint("Unhandled event: $type");
|
||||
}
|
||||
default:
|
||||
debugPrint("Unhandled event: $muksEventType");
|
||||
}
|
||||
debugPrint("Finished handling $muksEventType...");
|
||||
debugPrint("Finished handling $type...");
|
||||
} catch (error, stackTrace) {
|
||||
if (kDebugMode) {
|
||||
debugPrintStack(stackTrace: stackTrace, label: error.toString());
|
||||
|
|
|
|||
|
|
@ -17,6 +17,7 @@ import "package:nexus/models/content/name.dart";
|
|||
import "package:nexus/models/content/topic.dart";
|
||||
import "package:nexus/models/invited_room.dart";
|
||||
import "package:nexus/models/room_summary.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
|
||||
/// Pending invites, newest first.
|
||||
class InvitesController extends Notifier<IList<RoomSummary>> {
|
||||
|
|
@ -103,6 +104,15 @@ class InvitesController extends Notifier<IList<RoomSummary>> {
|
|||
.removeWhere((invite) => removed.contains(invite.roomId));
|
||||
}
|
||||
|
||||
void handleSync(SyncData sync) {
|
||||
if (sync.clearState) state = .new();
|
||||
update(
|
||||
sync.invitedRooms,
|
||||
joinedRooms: sync.rooms.keys.toISet(),
|
||||
leftRooms: sync.leftRooms,
|
||||
);
|
||||
}
|
||||
|
||||
void remove(String roomId) =>
|
||||
state = state.removeWhere((invite) => invite.roomId == roomId);
|
||||
|
||||
|
|
|
|||
|
|
@ -4,8 +4,10 @@ import "package:collection/collection.dart";
|
|||
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
import "package:nexus/models/event.dart";
|
||||
import "package:nexus/models/events_decrypted.dart";
|
||||
import "package:nexus/models/read_receipt.dart";
|
||||
import "package:nexus/models/room.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
|
||||
class RoomsController extends Notifier<IMap<String, Room>> {
|
||||
@override
|
||||
|
|
@ -82,6 +84,29 @@ class RoomsController extends Notifier<IMap<String, Room>> {
|
|||
),
|
||||
);
|
||||
|
||||
void handleSync(SyncData sync) {
|
||||
if (sync.clearState) state = .new();
|
||||
update(sync.rooms, sync.leftRooms);
|
||||
}
|
||||
|
||||
void handleDecrypted(EventsDecrypted decrypted) {
|
||||
final metadata = state[decrypted.roomId]?.metadata;
|
||||
|
||||
update(
|
||||
.new({
|
||||
decrypted.roomId: .new(
|
||||
events: decrypted.events,
|
||||
metadata: metadata?.copyWith(
|
||||
previewEventRowID:
|
||||
decrypted.previewEventRowID ?? metadata.previewEventRowID,
|
||||
sortingTimestamp:
|
||||
decrypted.sortingTimestamp ?? metadata.sortingTimestamp,
|
||||
),
|
||||
),
|
||||
}),
|
||||
);
|
||||
}
|
||||
|
||||
static IMap<String, ISet<int>> addRelations(
|
||||
IMap<String, ISet<int>> relations,
|
||||
Iterable<Event> events,
|
||||
|
|
|
|||
|
|
@ -1,13 +1,13 @@
|
|||
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
import "package:nexus/models/space_edge.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
|
||||
class SpaceEdgesController extends Notifier<IMap<String, IList<SpaceEdge>>> {
|
||||
@override
|
||||
IMap<String, IList<SpaceEdge>> build() => .new();
|
||||
|
||||
void set(IMap<String, IList<SpaceEdge>> newEdges) =>
|
||||
state = state.addAll(newEdges);
|
||||
void handleSync(SyncData sync) => state = sync.spaceEdges ?? state;
|
||||
|
||||
static final provider =
|
||||
NotifierProvider<SpaceEdgesController, IMap<String, IList<SpaceEdge>>>(
|
||||
|
|
|
|||
|
|
@ -1,11 +1,12 @@
|
|||
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
|
||||
class TopLevelSpacesController extends Notifier<IList<String>> {
|
||||
@override
|
||||
IList<String> build() => .new();
|
||||
|
||||
void set(IList<String> newSpaces) => state = newSpaces;
|
||||
void handleSync(SyncData sync) => state = sync.topLevelSpaces ?? state;
|
||||
|
||||
static final provider =
|
||||
NotifierProvider<TopLevelSpacesController, IList<String>>(
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
import "package:nexus/models/typing.dart";
|
||||
|
||||
class TypingController extends Notifier<IMap<String, IList<String>>> {
|
||||
|
|
@ -8,6 +9,10 @@ class TypingController extends Notifier<IMap<String, IList<String>>> {
|
|||
|
||||
void set(Typing typing) => state = state.add(typing.roomId, typing.userIds);
|
||||
|
||||
void handleSync(SyncData sync) {
|
||||
if (sync.clearState) state = .new();
|
||||
}
|
||||
|
||||
static final provider =
|
||||
NotifierProvider<TypingController, IMap<String, IList<String>>>(
|
||||
TypingController.new,
|
||||
|
|
|
|||
34
lib/models/gomuks_event.dart
Normal file
34
lib/models/gomuks_event.dart
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
import "package:freezed_annotation/freezed_annotation.dart";
|
||||
import "package:nexus/models/client_state.dart";
|
||||
import "package:nexus/models/event.dart";
|
||||
import "package:nexus/models/events_decrypted.dart";
|
||||
import "package:nexus/models/sync_data.dart";
|
||||
import "package:nexus/models/sync_status.dart";
|
||||
import "package:nexus/models/typing.dart";
|
||||
|
||||
part "gomuks_event.freezed.dart";
|
||||
|
||||
@freezed
|
||||
sealed class GomuksEvent with _$GomuksEvent {
|
||||
const factory GomuksEvent.clientState(ClientState state) = ClientStateEvent;
|
||||
const factory GomuksEvent.syncStatus(SyncStatus status) = SyncStatusEvent;
|
||||
const factory GomuksEvent.initComplete() = InitCompleteEvent;
|
||||
const factory GomuksEvent.sendComplete(Event event) = SendCompleteEvent;
|
||||
const factory GomuksEvent.typing(Typing typing) = TypingEvent;
|
||||
const factory GomuksEvent.eventsDecrypted(EventsDecrypted decrypted) =
|
||||
EventsDecryptedEvent;
|
||||
const factory GomuksEvent.syncComplete(SyncData sync) = SyncCompleteEvent;
|
||||
const factory GomuksEvent.unknown(String type) = UnknownGomuksEvent;
|
||||
|
||||
factory GomuksEvent.parse(String type, Map<String, dynamic> json) =>
|
||||
switch (type) {
|
||||
"client_state" => .clientState(.fromJson(json)),
|
||||
"sync_status" => .syncStatus(.fromJson(json)),
|
||||
"init_complete" => const .initComplete(),
|
||||
"send_complete" => .sendComplete(.fromJson(json["event"])),
|
||||
"typing" => .typing(.fromJson(json)),
|
||||
"events_decrypted" => .eventsDecrypted(.fromJson(json)),
|
||||
"sync_complete" => .syncComplete(.fromJson(json)),
|
||||
_ => .unknown(type),
|
||||
};
|
||||
}
|
||||
Loading…
Reference in a new issue