Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement User GraphQL subscription (#4) #7

Merged
merged 29 commits into from
Jul 11, 2022
Merged
Show file tree
Hide file tree
Changes from 26 commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
d05ee3a
Implement `User` GraphQL subscription
andrigel Jun 21, 2022
9cd02e9
Implement `User` GraphQL subscription
andrigel Jun 21, 2022
ef8e850
Implement `User` GraphQL subscription
andrigel Jun 21, 2022
0886d14
Implement `User` GraphQL subscription
andrigel Jun 21, 2022
c8ad797
Corrections
SleepySquash Jun 22, 2022
ef9aee5
Implement User GraphQL subscription
andrigel Jun 23, 2022
bdc3f5e
Implement User GraphQL subscription
andrigel Jun 23, 2022
2f1f4b4
Merge branch 'main' into 4-implement-user-graphql-subscription
andrigel Jun 23, 2022
9f92a3f
Implement User GraphQL subscription
andrigel Jun 23, 2022
7faa485
Corrections
SleepySquash Jun 24, 2022
5b683ee
Implement User GraphQL subscription
andrigel Jun 27, 2022
35fe4ef
Implement User GraphQL subscription
andrigel Jun 27, 2022
cdd332a
Implement `User` GraphQL subscription
andrigel Jun 28, 2022
e508685
Implement `User` GraphQL subscription
andrigel Jun 28, 2022
69a34e6
Implement `User` GraphQL subscription
andrigel Jun 28, 2022
d735e87
Implement User GraphQL subscription
andrigel Jun 28, 2022
8c67f1e
Merge remote-tracking branch 'origin/main' into 4-implement-user-grap…
SleepySquash Jul 1, 2022
c35e176
Corrections
SleepySquash Jul 1, 2022
66cb694
Implement User GraphQL subscription
andrigel Jul 4, 2022
3e4cb26
Corrections
SleepySquash Jul 5, 2022
12b9a4d
Merge remote-tracking branch 'origin/main' into 4-implement-user-grap…
SleepySquash Jul 5, 2022
3c8060f
Fix whitespace difference
SleepySquash Jul 5, 2022
831da7c
Add `KeyedSubtree` to chats
SleepySquash Jul 5, 2022
2483a5d
Improve mutex
SleepySquash Jul 5, 2022
3c4f715
Some corrections [skip ci]
tyranron Jul 8, 2022
d2a4830
corrections
andrigel Jul 8, 2022
b56fc5a
Implement User GraphQL subscription
andrigel Jul 8, 2022
010132d
Corrections
andrigel Jul 11, 2022
5dbc75e
Corrections
SleepySquash Jul 11, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,11 @@ All user visible changes to this project will be documented in this file. This p

[Diff](/../../compare/3aa35d5bf8ba9728f54db7bf4e21425711097cda...v0.1.0-alpha.6) | [Milestone](/../../milestone/1)

### Added

- UI:
- User information auto-updating on changes ([#7], [#4]).

### Fixed

- Android:
Expand All @@ -20,6 +25,8 @@ All user visible changes to this project will be documented in this file. This p
- Missing avatars in group creation popup ([#15], [#2]).

[#2]: /../../issues/2
[#4]: /../../issues/4
[#7]: /../../pull/7
[#14]: /../../pull/14
[#15]: /../../pull/15

Expand Down
61 changes: 61 additions & 0 deletions lib/api/backend/extension/user.dart
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
import '../schema.dart';
import '/domain/model/avatar.dart';
import '/domain/model/chat.dart';
import '/domain/model/crop_area.dart';
import '/domain/model/image_gallery_item.dart';
import '/domain/model/user_call_cover.dart';
import '/domain/model/user.dart';
Expand Down Expand Up @@ -84,3 +85,63 @@ extension ImageGalleryItemConversion on ImageGalleryItemMixin {
square: Square(square),
);
}

/// Extension adding models construction from
/// [UserEventsVersionedMixin$Events$EventUserGalleryItemAdded$GalleryItem].
extension EventUserGalleryItemAdded$GalleryItemConversion
on UserEventsVersionedMixin$Events$EventUserGalleryItemAdded$GalleryItem {
/// Constructs a new [ImageGalleryItem] from this
/// [UserEventsVersionedMixin$Events$EventUserGalleryItemAdded$GalleryItem].
ImageGalleryItem toModel() => (this as ImageGalleryItemMixin).toModel();
}

/// Extension adding models construction from an [UserAvatarMixin].
extension UserAvatarConversion on UserAvatarMixin {
andrigel marked this conversation as resolved.
Show resolved Hide resolved
/// Constructs a new [UserAvatar] from this [UserAvatarMixin].
UserAvatar toModel() => UserAvatar(
andrigel marked this conversation as resolved.
Show resolved Hide resolved
full: full,
original: original,
galleryItemId: galleryItemId,
big: big,
medium: medium,
small: small,
crop: crop != null
? CropArea(
topLeft: CropPoint(
x: crop!.topLeft.x,
y: crop!.topLeft.y,
),
bottomRight: CropPoint(
x: crop!.bottomRight.x,
y: crop!.bottomRight.y,
),
angle: crop?.angle,
)
: null,
);
}

/// Extension adding models construction from an [UserCallCoverMixin].
extension UserCallCoverConversion on UserCallCoverMixin {
/// Constructs a new [UserCallCover] from this [UserCallCoverMixin].
UserCallCover toModel() => UserCallCover(
galleryItemId: galleryItemId,
full: full,
original: original,
vertical: vertical,
square: square,
crop: crop != null
? CropArea(
topLeft: CropPoint(
x: crop!.topLeft.x,
y: crop!.topLeft.y,
),
bottomRight: CropPoint(
x: crop!.bottomRight.x,
y: crop!.bottomRight.y,
),
angle: crop?.angle,
)
: null,
);
}
38 changes: 38 additions & 0 deletions lib/api/backend/graphql/fragments/BlacklistEventsVersioned.graphql
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
# Copyright © 2022 IT ENGINEERING MANAGEMENT INC, <https://github.com/team113>
#
# This program is free software: you can redistribute it and/or modify it under
# the terms of the GNU Affero General Public License v3.0 as published by the
# Free Software Foundation, either version 3 of the License, or (at your
# option) any later version.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License v3.0 for
# more details.
#
# You should have received a copy of the GNU Affero General Public License v3.0
# along with this program. If not, see
# <https://www.gnu.org/licenses/agpl-3.0.html>.

fragment BlacklistEventsVersioned on BlacklistEventsVersioned {
events {
__typename
... on EventBlacklistRecordAdded {
userId
user {
...User
__typename
}
at
}
... on EventBlacklistRecordRemoved {
userId
user {
...User
__typename
}
at
}
}
myVer: ver
}
94 changes: 94 additions & 0 deletions lib/api/backend/graphql/fragments/UserEventsVersioned.graphql
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
# Copyright © 2022 IT ENGINEERING MANAGEMENT INC, <https://github.com/team113>
#
# This program is free software: you can redistribute it and/or modify it under
# the terms of the GNU Affero General Public License v3.0 as published by the
# Free Software Foundation, either version 3 of the License, or (at your
# option) any later version.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License v3.0 for
# more details.
#
# You should have received a copy of the GNU Affero General Public License v3.0
# along with this program. If not, see
# <https://www.gnu.org/licenses/agpl-3.0.html>.

fragment UserEventsVersioned on UserEventsVersioned {
events {
__typename
userId
... on EventUserAvatarDeleted {
at
}
... on EventUserAvatarUpdated {
avatar {
__typename
...UserAvatar
}
at
}
... on EventUserBioDeleted {
at
}
... on EventUserBioUpdated {
bio
at
}
... on EventUserCallCoverDeleted {
at
}
... on EventUserCallCoverUpdated {
callCover {
__typename
...UserCallCover
}
at
}
... on EventUserCameOffline {
at
}
... on EventUserCameOnline {
userId
}
... on EventUserDeleted {
at
}
... on EventUserNameDeleted {
at
}
... on EventUserGalleryItemAdded {
galleryItem {
__typename
... on ImageGalleryItem {
...ImageGalleryItem
}
}
at
}
... on EventUserGalleryItemDeleted {
galleryItemId
at
}
... on EventUserNameUpdated {
name
at
}
... on EventUserPresenceUpdated {
presence
at
}
... on EventUserStatusDeleted {
at
}
... on EventUserStatusUpdated {
status
at
}
}
user {
__typename
...User
}
ver
}
38 changes: 38 additions & 0 deletions lib/api/backend/graphql/subscription/user/UserEvents.graphql
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
# Copyright © 2022 IT ENGINEERING MANAGEMENT INC, <https://github.com/team113>
#
# This program is free software: you can redistribute it and/or modify it under
# the terms of the GNU Affero General Public License v3.0 as published by the
# Free Software Foundation, either version 3 of the License, or (at your
# option) any later version.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License v3.0 for
# more details.
#
# You should have received a copy of the GNU Affero General Public License v3.0
# along with this program. If not, see
# <https://www.gnu.org/licenses/agpl-3.0.html>.

subscription UserEvents($id: UserId!, $ver: UserVersion) {
andrigel marked this conversation as resolved.
Show resolved Hide resolved
userEvents(id: $id, ver: $ver) {
__typename
... on SubscriptionInitialized {
ok
}
... on User {
...User
}
... on UserEventsVersioned {
...UserEventsVersioned
}
... on BlacklistEventsVersioned {
...BlacklistEventsVersioned
}
... on IsBlacklisted {
blacklisted
myVer: ver
}
}
}

3 changes: 2 additions & 1 deletion lib/domain/repository/chat.dart
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import '../model/chat_item.dart';
import '../model/native_file.dart';
import '../model/user.dart';
import '../model/user_call_cover.dart';
import '../repository/user.dart';
import '/util/obs/obs.dart';

/// [Chat]s repository interface.
Expand Down Expand Up @@ -172,7 +173,7 @@ abstract class RxChat {
RxList<User> get typingUsers;

/// Reactive list of [User]s being members of this [chat].
RxMap<UserId, Rx<User>> get members;
RxMap<UserId, RxUser> get members;

/// Text representing the title of this [chat].
RxString get title;
Expand Down
6 changes: 5 additions & 1 deletion lib/domain/repository/contact.dart
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import 'package:get/get.dart';

import '../model/contact.dart';
import '../model/user.dart';
import '../repository/user.dart';
import '/util/obs/obs.dart';

/// [ChatContact]s repository interface.
Expand Down Expand Up @@ -63,6 +64,9 @@ abstract class RxChatContact {
/// Reactive value of the [ChatContact] this [RxChatContact] represents.
Rx<ChatContact> get contact;

/// Returns [ChatContactId] of the [contact].
ChatContactId get id => contact.value.id;

/// Reactive value of the first [User] this [ChatContact] contains.
Rx<Rx<User>?> get user;
Rx<RxUser?> get user;
}
29 changes: 23 additions & 6 deletions lib/domain/repository/user.dart
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ import '../model/user.dart';
/// [User]s repository interface.
abstract class AbstractUserRepository {
/// Returns reactive map of [User]s.
RxMap<UserId, Rx<User>> get users;
RxMap<UserId, RxUser> get users;

/// Indicates whether this repository was initialized and [users] can be
/// used.
Expand All @@ -41,23 +41,40 @@ abstract class AbstractUserRepository {
/// Searches [User]s by the provided [UserNum].
///
/// This is an exact match search.
Future<List<Rx<User>>> searchByNum(UserNum num);
Future<List<RxUser>> searchByNum(UserNum num);

/// Searches [User]s by the provided [UserLogin].
///
/// This is an exact match search.
Future<List<Rx<User>>> searchByLogin(UserLogin login);
Future<List<RxUser>> searchByLogin(UserLogin login);

/// Searches [User]s by the provided [UserName].
///
/// This is a fuzzy search.
Future<List<Rx<User>>> searchByName(UserName name);
Future<List<RxUser>> searchByName(UserName name);

/// Searches [User]s by the provided [ChatDirectLinkSlug].
///
/// This is an exact match search.
Future<List<Rx<User>>> searchByLink(ChatDirectLinkSlug link);
Future<List<RxUser>> searchByLink(ChatDirectLinkSlug link);

/// Returns an [User] by the provided [id].
Future<Rx<User>?> get(UserId id);
Future<RxUser?> get(UserId id);
}

/// Unified reactive [User] entity.
abstract class RxUser {
/// Returns reactive value of the [User] this [RxUser] represents.
Rx<User> get user;

/// Returns the [User.id] of this [RxUser].
UserId get id => user.value.id;

/// Increments counter of [User]'s updates listeners and starts listening the
/// updates if needed.
andrigel marked this conversation as resolved.
Show resolved Hide resolved
void listenUpdates();

/// Decrements counter of [User]'s updates listeners and stops listening
/// the updates if needed.
void stopUpdates();
}
Loading