mirror of
https://gitlab.com/famedly/fluffychat.git
synced 2025-02-17 06:20:44 +01:00
feat: notification actions android
unified push notifications seem to stop after one aciton, this is broken atm
This commit is contained in:
parent
78a5206ba7
commit
1ccb1642ac
@ -2518,5 +2518,7 @@
|
|||||||
"enterInviteLinkOrMatrixId": "Enter invite link or Matrix ID...",
|
"enterInviteLinkOrMatrixId": "Enter invite link or Matrix ID...",
|
||||||
"reopenChat": "Reopen chat",
|
"reopenChat": "Reopen chat",
|
||||||
"noBackupWarning": "Warning! Without enabling chat backup, you will lose access to your encrypted messages. It is highly recommended to enable the chat backup first before logging out.",
|
"noBackupWarning": "Warning! Without enabling chat backup, you will lose access to your encrypted messages. It is highly recommended to enable the chat backup first before logging out.",
|
||||||
"noOtherDevicesFound": "No other devices found"
|
"noOtherDevicesFound": "No other devices found",
|
||||||
|
"markRead": "Mark read",
|
||||||
|
"message": "Message"
|
||||||
}
|
}
|
@ -63,6 +63,9 @@ abstract class AppConfig {
|
|||||||
'https://github.com/googlefonts/noto-emoji/';
|
'https://github.com/googlefonts/noto-emoji/';
|
||||||
static const double borderRadius = 16.0;
|
static const double borderRadius = 16.0;
|
||||||
static const double columnWidth = 360.0;
|
static const double columnWidth = 360.0;
|
||||||
|
static const String markAsReadAction = 'markAsReadAction';
|
||||||
|
static const String replyAction = 'replyAction';
|
||||||
|
static const String notificationIsolate = 'notificationIsolate';
|
||||||
|
|
||||||
static void loadFromJson(Map<String, dynamic> json) {
|
static void loadFromJson(Map<String, dynamic> json) {
|
||||||
if (json['chat_color'] != null) {
|
if (json['chat_color'] != null) {
|
||||||
|
@ -20,6 +20,7 @@
|
|||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
import 'dart:isolate';
|
||||||
import 'dart:typed_data';
|
import 'dart:typed_data';
|
||||||
import 'dart:ui';
|
import 'dart:ui';
|
||||||
|
|
||||||
@ -72,6 +73,16 @@ class BackgroundPush {
|
|||||||
bool upAction = false;
|
bool upAction = false;
|
||||||
|
|
||||||
BackgroundPush._(this.client) {
|
BackgroundPush._(this.client) {
|
||||||
|
IsolateNameServer.removePortNameMapping(AppConfig.notificationIsolate);
|
||||||
|
final receivePort = ReceivePort();
|
||||||
|
|
||||||
|
IsolateNameServer.registerPortWithName(
|
||||||
|
receivePort.sendPort, AppConfig.notificationIsolate);
|
||||||
|
final backgroundMessagePort = receivePort.asBroadcastStream();
|
||||||
|
backgroundMessagePort.listen((event) async {
|
||||||
|
await notificationActionCallbacks(event);
|
||||||
|
});
|
||||||
|
|
||||||
onRoomSync ??= client.onSync.stream
|
onRoomSync ??= client.onSync.stream
|
||||||
.where((s) => s.hasRoomUpdate)
|
.where((s) => s.hasRoomUpdate)
|
||||||
.listen((s) => _onClearingPush(getFromServer: false));
|
.listen((s) => _onClearingPush(getFromServer: false));
|
||||||
@ -116,6 +127,29 @@ class BackgroundPush {
|
|||||||
}
|
}
|
||||||
|
|
||||||
StreamSubscription<SyncUpdate>? onRoomSync;
|
StreamSubscription<SyncUpdate>? onRoomSync;
|
||||||
|
Future<void> notificationActionCallbacks(Map response) async {
|
||||||
|
try {
|
||||||
|
if (response['payload'] == null) return;
|
||||||
|
Logs().d('Got response with action: ${response['actionId']}');
|
||||||
|
final roomId = json.decode(response['payload']!)['roomId'];
|
||||||
|
final eventId = json.decode(response['payload']!)['eventId'];
|
||||||
|
if (response['actionId'] == AppConfig.markAsReadAction) {
|
||||||
|
Logs().d('notification action setting read marker to $eventId');
|
||||||
|
await client.setReadMarker(roomId, eventId, mRead: eventId);
|
||||||
|
}
|
||||||
|
if (response['actionId'] == AppConfig.replyAction) {
|
||||||
|
Logs().d('notification action replying in room $roomId');
|
||||||
|
final sentEventId = await client
|
||||||
|
.getRoomById(roomId)!
|
||||||
|
.sendTextEvent(response['input'].toString());
|
||||||
|
if (sentEventId != null) {
|
||||||
|
await client.setReadMarker(roomId, sentEventId, mRead: sentEventId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
Logs().e('[BackgroundPushPlugin] error in notification actions', e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> setupPusher({
|
Future<void> setupPusher({
|
||||||
String? gatewayUrl,
|
String? gatewayUrl,
|
||||||
@ -282,7 +316,8 @@ class BackgroundPush {
|
|||||||
|
|
||||||
Future<void> goToRoom(NotificationResponse? response) async {
|
Future<void> goToRoom(NotificationResponse? response) async {
|
||||||
try {
|
try {
|
||||||
final roomId = response?.payload;
|
if (response == null || response.payload == null) return;
|
||||||
|
final roomId = jsonDecode(response.payload!)['roomId'];
|
||||||
Logs().v('[Push] Attempting to go to room $roomId...');
|
Logs().v('[Push] Attempting to go to room $roomId...');
|
||||||
if (router == null || roomId == null) {
|
if (router == null || roomId == null) {
|
||||||
return;
|
return;
|
||||||
@ -369,11 +404,13 @@ class BackgroundPush {
|
|||||||
json.decode(utf8.decode(message))['notification']);
|
json.decode(utf8.decode(message))['notification']);
|
||||||
// UP may strip the devices list
|
// UP may strip the devices list
|
||||||
data['devices'] ??= [];
|
data['devices'] ??= [];
|
||||||
|
Logs().e('showingaksdjf');
|
||||||
await pushHelper(
|
await pushHelper(
|
||||||
PushNotification.fromJson(data),
|
PushNotification.fromJson(data),
|
||||||
client: client,
|
client: client,
|
||||||
l10n: l10n,
|
l10n: l10n,
|
||||||
activeRoomId: router?.currentState?.pathParameters['roomid'],
|
activeRoomId: router?.currentState?.pathParameters['roomid'],
|
||||||
|
onSelectNotification: goToRoom,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -15,6 +15,21 @@ import 'package:fluffychat/utils/matrix_sdk_extensions/matrix_locals.dart';
|
|||||||
import 'package:fluffychat/utils/platform_infos.dart';
|
import 'package:fluffychat/utils/platform_infos.dart';
|
||||||
import 'package:fluffychat/utils/voip/callkeep_manager.dart';
|
import 'package:fluffychat/utils/voip/callkeep_manager.dart';
|
||||||
|
|
||||||
|
// Is triggered by `onDidReceiveBackgroundNotificationResponse` in a different isolate
|
||||||
|
// this gets cached btw (until new or uninstall). so even if you disable
|
||||||
|
// `onDidReceiveBackgroundNotificationResponse` the old `notificationTapBackground` will
|
||||||
|
// still function until replaced or app is reinstalled
|
||||||
|
@pragma('vm:entry-point')
|
||||||
|
void notificationTapBackground(NotificationResponse notificationResponse) {
|
||||||
|
final sendPort =
|
||||||
|
IsolateNameServer.lookupPortByName(AppConfig.notificationIsolate);
|
||||||
|
sendPort!.send({
|
||||||
|
'payload': notificationResponse.payload,
|
||||||
|
'actionId': notificationResponse.actionId,
|
||||||
|
'input': notificationResponse.input,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> pushHelper(
|
Future<void> pushHelper(
|
||||||
PushNotification notification, {
|
PushNotification notification, {
|
||||||
Client? client,
|
Client? client,
|
||||||
@ -41,7 +56,7 @@ Future<void> pushHelper(
|
|||||||
iOS: DarwinInitializationSettings(),
|
iOS: DarwinInitializationSettings(),
|
||||||
),
|
),
|
||||||
onDidReceiveNotificationResponse: onSelectNotification,
|
onDidReceiveNotificationResponse: onSelectNotification,
|
||||||
onDidReceiveBackgroundNotificationResponse: onSelectNotification,
|
// onDidReceiveBackgroundNotificationResponse: onSelectNotification,
|
||||||
);
|
);
|
||||||
flutterLocalNotificationsPlugin.show(
|
flutterLocalNotificationsPlugin.show(
|
||||||
0,
|
0,
|
||||||
@ -93,7 +108,7 @@ Future<void> _tryPushHelper(
|
|||||||
iOS: DarwinInitializationSettings(),
|
iOS: DarwinInitializationSettings(),
|
||||||
),
|
),
|
||||||
onDidReceiveNotificationResponse: onSelectNotification,
|
onDidReceiveNotificationResponse: onSelectNotification,
|
||||||
//onDidReceiveBackgroundNotificationResponse: onSelectNotification,
|
onDidReceiveBackgroundNotificationResponse: notificationTapBackground,
|
||||||
);
|
);
|
||||||
|
|
||||||
client ??= (await ClientManager.getClients(initialize: false)).first;
|
client ??= (await ClientManager.getClients(initialize: false)).first;
|
||||||
@ -197,6 +212,29 @@ Future<void> _tryPushHelper(
|
|||||||
AppConfig.pushNotificationsChannelName,
|
AppConfig.pushNotificationsChannelName,
|
||||||
channelDescription: AppConfig.pushNotificationsChannelDescription,
|
channelDescription: AppConfig.pushNotificationsChannelDescription,
|
||||||
number: notification.counts?.unread,
|
number: notification.counts?.unread,
|
||||||
|
actions: event.room.membership == Membership.join
|
||||||
|
? [
|
||||||
|
if (event.room.canSendEvent('m.read') &&
|
||||||
|
event.room.canSendEvent('m.fully_read'))
|
||||||
|
AndroidNotificationAction(
|
||||||
|
AppConfig.markAsReadAction,
|
||||||
|
l10n.markRead,
|
||||||
|
showsUserInterface: false,
|
||||||
|
),
|
||||||
|
if (event.room.canSendEvent(EventTypes.Message))
|
||||||
|
AndroidNotificationAction(
|
||||||
|
AppConfig.replyAction,
|
||||||
|
l10n.reply,
|
||||||
|
showsUserInterface: false,
|
||||||
|
inputs: [
|
||||||
|
AndroidNotificationActionInput(
|
||||||
|
label: l10n.message,
|
||||||
|
allowedMimeTypes: <String>{'text/plain'},
|
||||||
|
)
|
||||||
|
],
|
||||||
|
)
|
||||||
|
]
|
||||||
|
: [],
|
||||||
styleInformation: messagingStyleInformation ??
|
styleInformation: messagingStyleInformation ??
|
||||||
MessagingStyleInformation(
|
MessagingStyleInformation(
|
||||||
Person(name: event.room.client.userID),
|
Person(name: event.room.client.userID),
|
||||||
@ -208,7 +246,6 @@ Future<void> _tryPushHelper(
|
|||||||
),
|
),
|
||||||
ticker: l10n.unreadChats(notification.counts?.unread ?? 1),
|
ticker: l10n.unreadChats(notification.counts?.unread ?? 1),
|
||||||
importance: Importance.max,
|
importance: Importance.max,
|
||||||
priority: Priority.high,
|
|
||||||
groupKey: event.room.id,
|
groupKey: event.room.id,
|
||||||
);
|
);
|
||||||
const iOSPlatformChannelSpecifics = DarwinNotificationDetails();
|
const iOSPlatformChannelSpecifics = DarwinNotificationDetails();
|
||||||
@ -224,7 +261,7 @@ Future<void> _tryPushHelper(
|
|||||||
),
|
),
|
||||||
body,
|
body,
|
||||||
platformChannelSpecifics,
|
platformChannelSpecifics,
|
||||||
payload: event.roomId,
|
payload: json.encode({'roomId': event.roomId, 'eventId': event.eventId}),
|
||||||
);
|
);
|
||||||
Logs().v('Push helper has been completed!');
|
Logs().v('Push helper has been completed!');
|
||||||
}
|
}
|
||||||
|
57
pubspec.lock
57
pubspec.lock
@ -293,10 +293,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: dbus
|
name: dbus
|
||||||
sha256: "4f814fc7e73057f78f307a6c4714fe2ffb4bdb994ab1970540a068ec4d5a45be"
|
sha256: "6f07cba3f7b3448d42d015bfd3d53fe12e5b36da2423f23838efc1d5fb31a263"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.7.3"
|
version: "0.7.8"
|
||||||
desktop_drop:
|
desktop_drop:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -614,19 +614,20 @@ packages:
|
|||||||
flutter_local_notifications:
|
flutter_local_notifications:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
name: flutter_local_notifications
|
path: flutter_local_notifications
|
||||||
sha256: f222919a34545931e47b06000836b5101baeffb0e6eb5a4691d2d42851740dd9
|
ref: "v13.1.0"
|
||||||
url: "https://pub.dev"
|
resolved-ref: af8082bc65d281e4485b41d0a8b72614627fbb1c
|
||||||
source: hosted
|
url: "https://gitlab.com/techno_disaster/flutter_local_notifications.git"
|
||||||
version: "12.0.4"
|
source: git
|
||||||
|
version: "13.1.0"
|
||||||
flutter_local_notifications_linux:
|
flutter_local_notifications_linux:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: flutter_local_notifications_linux
|
name: flutter_local_notifications_linux
|
||||||
sha256: "6af440e3962eeab8459602c309d7d4ab9e62f05d5cfe58195a28f846a0b5d523"
|
sha256: "8f6c1611e0c4a88a382691a97bb3c3feb24cc0c0b54152b8b5fb7ffb837f7fbf"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.0.0"
|
version: "3.0.0"
|
||||||
flutter_local_notifications_platform_interface:
|
flutter_local_notifications_platform_interface:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -649,13 +650,13 @@ packages:
|
|||||||
source: hosted
|
source: hosted
|
||||||
version: "3.1.0"
|
version: "3.1.0"
|
||||||
flutter_math_fork:
|
flutter_math_fork:
|
||||||
dependency: transitive
|
dependency: "direct overridden"
|
||||||
description:
|
description:
|
||||||
name: flutter_math_fork
|
name: flutter_math_fork
|
||||||
sha256: cfec964c4975c6becc64291eb9b782fe70df5e0c5bfe0763d9e856432fcc6fcd
|
sha256: fa511bdcb91fc35eac155ec5790883886dd9de6572fea549f1ad4660ef6804e9
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.4.2+2"
|
version: "0.6.3+1"
|
||||||
flutter_matrix_html:
|
flutter_matrix_html:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -668,10 +669,10 @@ packages:
|
|||||||
dependency: "direct dev"
|
dependency: "direct dev"
|
||||||
description:
|
description:
|
||||||
name: flutter_native_splash
|
name: flutter_native_splash
|
||||||
sha256: bd36d1a7f05ff8378cad17d20c33ca904630bfd3fcf8b15c9e8237efbccfad0a
|
sha256: "6777a3abb974021a39b5fdd2d46a03ca390e03903b6351f21d10e7ecc969f12d"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.2.0+1"
|
version: "2.2.16"
|
||||||
flutter_olm:
|
flutter_olm:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -757,10 +758,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: flutter_svg
|
name: flutter_svg
|
||||||
sha256: "9ac1967e2f72a08af11b05b39167920f90d043cf67163d13a544a358c8f31afa"
|
sha256: "6ff9fa12892ae074092de2fa6a9938fb21dbabfdaa2ff57dc697ff912fc8d4b2"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.22.0"
|
version: "1.1.6"
|
||||||
flutter_test:
|
flutter_test:
|
||||||
dependency: "direct dev"
|
dependency: "direct dev"
|
||||||
description: flutter
|
description: flutter
|
||||||
@ -933,10 +934,10 @@ packages:
|
|||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
name: image
|
name: image
|
||||||
sha256: "02bafd3b4f399bfeb10034deba9753d93b55ce41cd0c4d3d8b355626f80e5b32"
|
sha256: "8e9d133755c3e84c73288363e6343157c383a0c6c56fc51afcc5d4d7180306d6"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.1.3"
|
version: "3.3.0"
|
||||||
image_picker:
|
image_picker:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -1079,14 +1080,6 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.8.1"
|
version: "0.8.1"
|
||||||
lint:
|
|
||||||
dependency: transitive
|
|
||||||
description:
|
|
||||||
name: lint
|
|
||||||
sha256: "4a539aa34ec5721a2c7574ae2ca0336738ea4adc2a34887d54b7596310b33c85"
|
|
||||||
url: "https://pub.dev"
|
|
||||||
source: hosted
|
|
||||||
version: "1.10.0"
|
|
||||||
lints:
|
lints:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -1323,18 +1316,18 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: path_drawing
|
name: path_drawing
|
||||||
sha256: "3bdd251dae9ffaef944450b73f168610db7e968e7b20daf0c3907f8b4aafc8a2"
|
sha256: bbb1934c0cbb03091af082a6389ca2080345291ef07a5fa6d6e078ba8682f977
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.5.1+1"
|
version: "1.0.1"
|
||||||
path_parsing:
|
path_parsing:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: path_parsing
|
name: path_parsing
|
||||||
sha256: ee5c47c1058ad66b4a41746ec3996af9593d0858872807bcd64ac118f0700337
|
sha256: e3e67b1629e6f7e8100b367d3db6ba6af4b1f0bb80f64db18ef1fbabd2fa9ccf
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.2.1"
|
version: "1.0.1"
|
||||||
path_provider:
|
path_provider:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -2264,10 +2257,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: xml
|
name: xml
|
||||||
sha256: "80d494c09849dc3f899d227a78c30c5b949b985ededf884cb3f3bcd39f4b447a"
|
sha256: "979ee37d622dec6365e2efa4d906c37470995871fe9ae080d967e192d88286b5"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "5.4.1"
|
version: "6.2.2"
|
||||||
yaml:
|
yaml:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
10
pubspec.yaml
10
pubspec.yaml
@ -147,6 +147,16 @@ dependency_overrides:
|
|||||||
# This otherwise breaks on linux with flutter 3.7.0, let's override it for now.
|
# This otherwise breaks on linux with flutter 3.7.0, let's override it for now.
|
||||||
file_selector: ^0.9.2+2
|
file_selector: ^0.9.2+2
|
||||||
file_selector_linux: ^0.9.1
|
file_selector_linux: ^0.9.1
|
||||||
|
# because unified push and flutter isolate both have a flutter engine spawned
|
||||||
|
# automatically, this fork uses those cached engine for notification actions
|
||||||
|
# on android
|
||||||
|
flutter_local_notifications:
|
||||||
|
git:
|
||||||
|
url: https://gitlab.com/techno_disaster/flutter_local_notifications.git
|
||||||
|
path: flutter_local_notifications
|
||||||
|
ref: v13.1.0
|
||||||
|
# dependency hell
|
||||||
|
flutter_math_fork: ^0.6.3+1
|
||||||
# fake secure storage plugin for Windows
|
# fake secure storage plugin for Windows
|
||||||
# See: https://gitlab.com/gitlab-com/gl-infra/reliability/-/issues/15161
|
# See: https://gitlab.com/gitlab-com/gl-infra/reliability/-/issues/15161
|
||||||
flutter_secure_storage_windows:
|
flutter_secure_storage_windows:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user