From 1521558304f536eea2baa8c3ac75a51eeb8edd81 Mon Sep 17 00:00:00 2001 From: Sahil Kumar Date: Wed, 27 Jan 2021 12:52:37 +0530 Subject: [PATCH] Make `stream_chat_persistence` a add on dependency instead of shipping it with the llc Signed-off-by: Sahil Kumar --- packages/dart_client/lib/src/api/channel.dart | 18 +++-- packages/dart_client/lib/src/client.dart | 55 ++++++-------- ...ence.dart => chat_persistence_client.dart} | 13 ++-- .../dart_client/lib/src/notifications.dart | 54 ++++---------- packages/dart_client/lib/stream_chat.dart | 2 +- .../example/lib/advanced_options_page.dart | 74 ++----------------- .../flutter_widgets/example/lib/main.dart | 9 ++- .../example/lib/notifications_service.dart | 14 +++- .../example/lib/routes/app_routes.dart | 6 ++ .../example/lib/routes/routes.dart | 1 + packages/flutter_widgets/example/pubspec.yaml | 4 +- .../lib/src/db/shared/unsupported_db.dart | 2 +- .../lib/src/mapper/channel_mapper.dart | 1 - ...rt => stream_chat_persistence_client.dart} | 61 ++++++++------- .../lib/stream_chat_persistence.dart | 2 +- packages/stream_chat_persistence/pubspec.yaml | 1 + 16 files changed, 128 insertions(+), 189 deletions(-) rename packages/dart_client/lib/src/db/{stream_chat_persistence.dart => chat_persistence_client.dart} (95%) rename packages/stream_chat_persistence/lib/src/{stream_chat_persistence_impl.dart => stream_chat_persistence_client.dart} (79%) diff --git a/packages/dart_client/lib/src/api/channel.dart b/packages/dart_client/lib/src/api/channel.dart index a8952e34..3ba9aa1f 100644 --- a/packages/dart_client/lib/src/api/channel.dart +++ b/packages/dart_client/lib/src/api/channel.dart @@ -419,7 +419,7 @@ class Channel { } } - await _client.chatPersistence?.deleteMessageById(messageId); + await _client.chatPersistenceClient?.deleteMessageById(messageId); } return res; @@ -487,7 +487,7 @@ class Channel { PaginationParams options, { bool preferOffline = false, }) async { - final cachedReplies = await _client.chatPersistence?.getReplies( + final cachedReplies = await _client.chatPersistenceClient?.getReplies( parentId, lessThan: options?.lessThan, ); @@ -603,7 +603,8 @@ class Channel { } if (preferOffline && cid != null) { - final updatedState = await _client.chatPersistence?.getChannelStateByCid( + final updatedState = + await _client.chatPersistenceClient?.getChannelStateByCid( cid, messagePagination: messagesPagination, ); @@ -730,7 +731,7 @@ class Channel { if (clearHistory == true) { state.truncate(); - await _client.chatPersistence?.deleteMessageByCid(_cid); + await _client.chatPersistenceClient?.deleteMessageByCid(_cid); } return _client.decode(response.data, EmptyResponse.fromJson); @@ -869,7 +870,7 @@ class ChannelClientState { _computeInitialUnread(); - _channel._client.chatPersistence + _channel._client.chatPersistenceClient ?.getChannelThreads(_channel.cid) ?.then((threads) { _threads = threads; @@ -947,7 +948,8 @@ class ChannelClientState { .on(EventType.channelTruncated, EventType.notificationChannelTruncated) .listen((event) async { final channel = event.channel; - await _channel._client.chatPersistence?.deleteMessageByCid(channel.cid); + await _channel._client.chatPersistenceClient + ?.deleteMessageByCid(channel.cid); truncate(); })); } @@ -1401,7 +1403,7 @@ class ChannelClientState { set _channelState(ChannelState v) { _channelStateController.add(v); - _channel._client.chatPersistence?.updateChannelState(v); + _channel._client.chatPersistenceClient?.updateChannelState(v); } /// The channel threads related to this channel @@ -1414,7 +1416,7 @@ class ChannelClientState { BehaviorSubject.seeded({}); set _threads(Map> v) { - _channel._client.chatPersistence?.updateMessages( + _channel._client.chatPersistenceClient?.updateMessages( _channel.cid, v.values.expand((v) => v).toList(), ); diff --git a/packages/dart_client/lib/src/client.dart b/packages/dart_client/lib/src/client.dart index 99350636..714acbd5 100644 --- a/packages/dart_client/lib/src/client.dart +++ b/packages/dart_client/lib/src/client.dart @@ -6,7 +6,6 @@ import 'package:dio/dio.dart'; import 'package:flutter/cupertino.dart'; import 'package:logging/logging.dart'; import 'package:rxdart/rxdart.dart'; -import 'package:stream_chat_persistence/stream_chat_persistence.dart'; import 'package:shared_preferences/shared_preferences.dart'; import 'package:stream_chat/src/api/retry_policy.dart'; import 'package:stream_chat/src/event_type.dart'; @@ -21,7 +20,7 @@ import 'api/connection_status.dart'; import 'api/requests.dart'; import 'api/responses.dart'; import 'api/websocket.dart'; -import 'db/stream_chat_persistence.dart'; +import 'db/chat_persistence_client.dart'; import 'exceptions.dart'; import 'models/event.dart'; import 'models/message.dart'; @@ -87,7 +86,6 @@ class Client { this.baseURL = _defaultBaseURL, this.logLevel = Level.WARNING, this.logHandlerFunction, - this.persistenceEnabled = true, Duration connectTimeout = const Duration(seconds: 6), Duration receiveTimeout = const Duration(seconds: 6), Dio httpClient, @@ -111,10 +109,11 @@ class Client { logger.info('instantiating new client'); } - StreamChatPersistence _chatPersistence; + /// Client chat persistence client + ChatPersistenceClient chatPersistenceClient; - /// If true chat data will persist on disk - final bool persistenceEnabled; + /// Whether the chat persistence is available or not + bool get persistenceEnabled => chatPersistenceClient != null; RetryPolicy _retryPolicy; @@ -131,9 +130,6 @@ class Client { /// The amount of time that will pass before disconnecting the client in the background final Duration backgroundKeepAlive; - /// Client offline database - StreamChatPersistence get chatPersistence => _chatPersistence; - /// This client state ClientState state; @@ -345,7 +341,7 @@ class Client { /// Call this function to dispose the client void dispose() async { - await _chatPersistence?.disconnect(); + await chatPersistenceClient?.disconnect(); await _disconnect(); httpClient.close(); await _controller.close(); @@ -427,8 +423,8 @@ class Client { if (!event.isLocal) { if (_synced && event.createdAt != null) { - await _chatPersistence?.updateConnectionInfo(event); - await _chatPersistence?.updateLastSyncAt(event.createdAt); + await chatPersistenceClient?.updateConnectionInfo(event); + await chatPersistenceClient?.updateLastSyncAt(event.createdAt); } } @@ -459,12 +455,8 @@ class Client { wsConnectionStatus.value = ConnectionStatus.connecting; - if (persistenceEnabled && _chatPersistence == null) { - _chatPersistence = StreamChatPersistenceImpl( - state.user.id, - logger: _detachedLogger('💽'), - ); - await _chatPersistence.connect(); + if (persistenceEnabled) { + await chatPersistenceClient.connect('db_${state.user.id}'); } _ws = WebSocket( @@ -514,10 +506,10 @@ class Client { _ws.connectionStatus.addListener(_connectionStatusListener); - var event = await _chatPersistence?.getConnectionInfo(); + var event = await chatPersistenceClient?.getConnectionInfo(); await _ws.connect().then((e) async { - await _chatPersistence?.updateConnectionInfo(e); + await chatPersistenceClient?.updateConnectionInfo(e); event = e; await resync(); }).catchError((err, stacktrace) { @@ -532,14 +524,14 @@ class Client { /// Get the events missed while offline to sync the offline storage Future resync([List cids]) async { - final lastSyncAt = await chatPersistence?.getLastSyncAt(); + final lastSyncAt = await chatPersistenceClient?.getLastSyncAt(); if (lastSyncAt == null) { _synced = true; return; } - cids ??= await chatPersistence?.getChannelCids(); + cids ??= await chatPersistenceClient?.getChannelCids(); if (cids?.isEmpty == true) { return; @@ -568,7 +560,7 @@ class Client { handleEvent(event); }); - await _chatPersistence?.updateLastSyncAt(DateTime.now()); + await chatPersistenceClient?.updateLastSyncAt(DateTime.now()); _synced = true; } catch (error) { logger.severe('Error during resync $error'); @@ -714,7 +706,7 @@ class Client { channels.add(channel); } else { final newChannel = Channel.fromState(this, channelState); - await _chatPersistence + await chatPersistenceClient ?.updateChannelState(newChannel.state.channelState); newChannel.state?.updateChannelState(channelState); newChannels[newChannel.cid] = newChannel; @@ -725,7 +717,7 @@ class Client { state.channels = newChannels; - await _chatPersistence?.updateChannelQueries( + await chatPersistenceClient?.updateChannelQueries( filter, res.channels.map((c) => c.channel.cid).toList(), paginationParams?.offset == null || paginationParams.offset == 0, @@ -760,7 +752,7 @@ class Client { @required List sort, PaginationParams paginationParams = const PaginationParams(limit: 10), }) async { - final offlineChannels = await _chatPersistence?.getChannelStates( + final offlineChannels = await chatPersistenceClient?.getChannelStates( filter: filter, sort: sort, paginationParams: paginationParams, @@ -775,7 +767,8 @@ class Client { return channel; } else { final newChannel = Channel.fromState(this, channelState); - _chatPersistence?.updateChannelState(newChannel.state.channelState); + chatPersistenceClient + ?.updateChannelState(newChannel.state.channelState); newChannels[newChannel.cid] = newChannel; return newChannel; } @@ -938,8 +931,8 @@ class Client { logger.info( 'Disconnecting flushOfflineStorage: $flushChatPersistence; clearUser: $clearUser'); - await _chatPersistence?.disconnect(flush: flushChatPersistence); - _chatPersistence = null; + await chatPersistenceClient?.disconnect(flush: flushChatPersistence); + chatPersistenceClient = null; if (clearUser == true) { state.dispose(); @@ -1328,7 +1321,7 @@ class ClientState { void _listenChannelHidden() { _subscriptions.add(_client.on(EventType.channelHidden).listen((event) { - _client._chatPersistence?.deleteChannels([event.cid]); + _client.chatPersistenceClient?.deleteChannels([event.cid]); if (channels != null) { channels = channels..removeWhere((cid, ch) => cid == event.cid); } @@ -1353,7 +1346,7 @@ class ClientState { ) .listen((Event event) async { final eventChannel = event.channel; - await _client._chatPersistence?.deleteChannels([eventChannel.cid]); + await _client.chatPersistenceClient?.deleteChannels([eventChannel.cid]); if (channels != null) { channels = channels..remove(eventChannel.cid); } diff --git a/packages/dart_client/lib/src/db/stream_chat_persistence.dart b/packages/dart_client/lib/src/db/chat_persistence_client.dart similarity index 95% rename from packages/dart_client/lib/src/db/stream_chat_persistence.dart rename to packages/dart_client/lib/src/db/chat_persistence_client.dart index 40004825..c435df9e 100644 --- a/packages/dart_client/lib/src/db/stream_chat_persistence.dart +++ b/packages/dart_client/lib/src/db/chat_persistence_client.dart @@ -9,15 +9,12 @@ import 'package:stream_chat/src/models/read.dart'; import 'package:stream_chat/src/models/user.dart'; /// -abstract class StreamChatPersistence { - /// Creates a new connection to the database - Future connect({ - bool connectBackground = false, - bool logStatements = false, - }); +abstract class ChatPersistenceClient { + /// Creates a new connection to the client + Future connect(String name); - /// Closes the database instance - /// If [flush] is true, the database data will be deleted + /// Closes the client connection + /// If [flush] is true, the data will also be deleted Future disconnect({bool flush = false}); /// Get stored replies by messageId diff --git a/packages/dart_client/lib/src/notifications.dart b/packages/dart_client/lib/src/notifications.dart index e4cef9b5..82070fd2 100644 --- a/packages/dart_client/lib/src/notifications.dart +++ b/packages/dart_client/lib/src/notifications.dart @@ -1,12 +1,11 @@ import 'dart:convert'; -import 'package:logging/logging.dart'; import 'package:shared_preferences/shared_preferences.dart'; import 'package:stream_chat/src/api/responses.dart'; import 'package:stream_chat/src/models/channel_model.dart'; import 'package:stream_chat/src/models/channel_state.dart'; import 'package:stream_chat/src/models/message.dart'; -import 'package:stream_chat_persistence/stream_chat_persistence.dart'; +import 'package:meta/meta.dart'; import 'client.dart'; import 'models/own_user.dart'; @@ -20,21 +19,13 @@ class NotificationService { ) async { if (message != null && client.persistenceEnabled) { if (client?.state?.channels == null) { - final sharedPreferences = await _getSharedPreferences(); - final userId = sharedPreferences.getString(KEY_USER_ID); - - final chatPersistence = StreamChatPersistenceImpl( - userId, - logger: Logger('💽'), - ); - await chatPersistence.connect(); - await chatPersistence.updateChannelState( + final chatPersistenceClient = client.chatPersistenceClient; + await chatPersistenceClient.updateChannelState( ChannelState( channel: channelModel, messages: [message], ), ); - await chatPersistence.disconnect(); } else { final channel = client.state.channels[channelModel.cid]; channel.state.updateChannelState( @@ -56,14 +47,11 @@ class NotificationService { /// Gets the message using the client without storing it in the offline storage /// It returns an object containing the information about the message and the channel - static Future getMessage(String messageId) async { + static Future _getMessage(String messageId) async { final sharedPreferences = await _getSharedPreferences(); final apiKey = sharedPreferences.getString(KEY_API_KEY); - final client = Client( - apiKey, - persistenceEnabled: false, - ); + final client = Client(apiKey); final userId = sharedPreferences.getString(KEY_USER_ID); final token = sharedPreferences.getString(KEY_TOKEN); @@ -74,30 +62,16 @@ class NotificationService { return res; } - /// Stores the message in the offline storage - static Future storeMessage(GetMessageResponse messageResponse) async { - final sharedPreferences = await _getSharedPreferences(); - final userId = sharedPreferences.getString(KEY_USER_ID); - - final chatPersistence = StreamChatPersistenceImpl( - userId, - logger: Logger('💽'), - ); - await chatPersistence.connect(); - - await chatPersistence.updateChannelState(ChannelState( - messages: [messageResponse.message], - channel: messageResponse.channel, - )); - - await chatPersistence.disconnect(); - } - - /// Gets the message using the client and stores it in the offline storage + /// Gets the message using the client and calls a [storeMessageHandler] callback + /// with the message if the user wants to save the message in db + /// /// It returns an object containing the information about the message and the channel - static Future getAndStoreMessage(String messageId) async { - final getMessageResponse = await getMessage(messageId); - await storeMessage(getMessageResponse); + static Future getAndStoreMessage({ + @required String messageId, + @required Future Function(GetMessageResponse) storeMessageHandler, + }) async { + final getMessageResponse = await _getMessage(messageId); + await storeMessageHandler(getMessageResponse); return getMessageResponse; } diff --git a/packages/dart_client/lib/stream_chat.dart b/packages/dart_client/lib/stream_chat.dart index 0ff1f871..00525b40 100644 --- a/packages/dart_client/lib/stream_chat.dart +++ b/packages/dart_client/lib/stream_chat.dart @@ -27,4 +27,4 @@ export './src/models/reaction.dart'; export './src/models/read.dart'; export './src/models/user.dart'; export './src/notifications.dart'; -export './src/db/stream_chat_persistence.dart'; \ No newline at end of file +export './src/db/chat_persistence_client.dart'; diff --git a/packages/flutter_widgets/example/lib/advanced_options_page.dart b/packages/flutter_widgets/example/lib/advanced_options_page.dart index 023ce32c..915bcfcb 100644 --- a/packages/flutter_widgets/example/lib/advanced_options_page.dart +++ b/packages/flutter_widgets/example/lib/advanced_options_page.dart @@ -8,9 +8,11 @@ import 'package:flutter/material.dart'; import 'package:flutter/services.dart'; import 'package:flutter_secure_storage/flutter_secure_storage.dart'; import 'package:stream_chat_flutter/stream_chat_flutter.dart'; +import 'package:stream_chat_persistence/stream_chat_persistence.dart'; import 'package:streaming_shared_preferences/streaming_shared_preferences.dart'; import 'choose_user_page.dart'; +import 'main.dart'; import 'notifications_service.dart'; class AdvancedOptionsPage extends StatefulWidget { @@ -278,8 +280,7 @@ class _AdvancedOptionsPageState extends State { showLocalNotification: (!kIsWeb && Platform.isAndroid) ? showLocalNotification : null, - persistenceEnabled: true, - ); + )..chatPersistenceClient = chatPersistentClient; try { await client.setUser( @@ -320,72 +321,13 @@ class _AdvancedOptionsPageState extends State { return; } - if (!kIsWeb) { - initNotifications(client); - } - Navigator.pop(context); - Navigator.pop(context); - await Navigator.pushReplacement( - context, - MaterialPageRoute( - builder: (context) { - return FutureBuilder( - future: StreamingSharedPreferences.instance, - builder: (context, snapshot) { - if (!snapshot.hasData) { - return SizedBox(); - } - return PreferenceBuilder( - preference: snapshot.data.getInt( - 'theme', - defaultValue: 0, - ), - builder: (context, snapshot) => MaterialApp( - builder: (context, child) { - return StreamChat( - client: client, - child: Builder( - builder: (context) => - AnnotatedRegion< - SystemUiOverlayStyle>( - child: child, - value: SystemUiOverlayStyle( - systemNavigationBarColor: - StreamChatTheme.of(context) - .colorTheme - .white, - systemNavigationBarIconBrightness: - Theme.of(context) - .brightness == - Brightness.dark - ? Brightness.light - : Brightness.dark, - ), - ), - ), - ); - }, - debugShowCheckedModeBanner: false, - theme: ThemeData.light(), - darkTheme: ThemeData.dark(), - themeMode: { - -1: ThemeMode.dark, - 0: ThemeMode.system, - 1: ThemeMode.light, - }[snapshot], - onGenerateRoute: AppRoutes.generateRoute, - initialRoute: client.state.user == null - ? Routes.CHOOSE_USER - : Routes.HOME, - ), - ); - }, - ); - }, - ), - ); loading = false; + await Navigator.pushReplacementNamed( + context, + Routes.APP, + arguments: client, + ); } }, ), diff --git a/packages/flutter_widgets/example/lib/main.dart b/packages/flutter_widgets/example/lib/main.dart index 10d73997..caa11198 100644 --- a/packages/flutter_widgets/example/lib/main.dart +++ b/packages/flutter_widgets/example/lib/main.dart @@ -10,6 +10,7 @@ import 'package:flutter/material.dart'; import 'package:flutter/services.dart'; import 'package:flutter_secure_storage/flutter_secure_storage.dart'; import 'package:stream_chat_flutter/stream_chat_flutter.dart'; +import 'package:stream_chat_persistence/stream_chat_persistence.dart'; import 'package:streaming_shared_preferences/streaming_shared_preferences.dart'; import 'notifications_service.dart'; @@ -17,6 +18,11 @@ import 'routes/app_routes.dart'; import 'routes/routes.dart'; import 'search_text_field.dart'; +final chatPersistentClient = StreamChatPersistenceClient( + logLevel: Level.INFO, + connectionMode: ConnectionMode.background, +); + void main() async { WidgetsFlutterBinding.ensureInitialized(); final secureStorage = FlutterSecureStorage(); @@ -29,8 +35,7 @@ void main() async { logLevel: Level.INFO, showLocalNotification: (!kIsWeb && Platform.isAndroid) ? showLocalNotification : null, - persistenceEnabled: true, - ); + )..chatPersistenceClient = chatPersistentClient; if (userId != null) { final token = await secureStorage.read(key: kStreamToken); diff --git a/packages/flutter_widgets/example/lib/notifications_service.dart b/packages/flutter_widgets/example/lib/notifications_service.dart index 298ab3ab..0eeb9cc0 100644 --- a/packages/flutter_widgets/example/lib/notifications_service.dart +++ b/packages/flutter_widgets/example/lib/notifications_service.dart @@ -1,5 +1,6 @@ import 'dart:io'; +import 'package:example/main.dart'; import 'package:flutter_apns/flutter_apns.dart'; import 'package:flutter_local_notifications/flutter_local_notifications.dart' hide Message; @@ -36,8 +37,17 @@ Future backgroundHandler(Map notification) async { print('new notification ${notification}'); final messageId = notification['data']['id']; - final notificationData = - await NotificationService.getAndStoreMessage(messageId); + final notificationData = await NotificationService.getAndStoreMessage( + messageId: messageId, + storeMessageHandler: (messageResponse) { + return chatPersistentClient.updateChannelState( + ChannelState( + messages: [messageResponse.message], + channel: messageResponse.channel, + ), + ); + }, + ); showLocalNotification( notificationData.message, diff --git a/packages/flutter_widgets/example/lib/routes/app_routes.dart b/packages/flutter_widgets/example/lib/routes/app_routes.dart index 0c8a899f..e7c7e318 100644 --- a/packages/flutter_widgets/example/lib/routes/app_routes.dart +++ b/packages/flutter_widgets/example/lib/routes/app_routes.dart @@ -15,6 +15,12 @@ class AppRoutes { static Route generateRoute(RouteSettings settings) { final args = settings.arguments; switch (settings.name) { + case Routes.APP: + return MaterialPageRoute( + settings: const RouteSettings(name: Routes.APP), + builder: (_) { + return MyApp(args); + }); case Routes.HOME: return MaterialPageRoute( settings: const RouteSettings(name: Routes.HOME), diff --git a/packages/flutter_widgets/example/lib/routes/routes.dart b/packages/flutter_widgets/example/lib/routes/routes.dart index 0d2f4e5f..2280ca30 100644 --- a/packages/flutter_widgets/example/lib/routes/routes.dart +++ b/packages/flutter_widgets/example/lib/routes/routes.dart @@ -1,5 +1,6 @@ /// Define all the route names here class Routes { + static const String APP = '/app'; static const String HOME = '/home'; static const String CHOOSE_USER = '/choose_user'; static const String ADVANCED_OPTIONS = '/advance_options'; diff --git a/packages/flutter_widgets/example/pubspec.yaml b/packages/flutter_widgets/example/pubspec.yaml index fea15136..1a3f93df 100644 --- a/packages/flutter_widgets/example/pubspec.yaml +++ b/packages/flutter_widgets/example/pubspec.yaml @@ -9,8 +9,10 @@ environment: dependencies: flutter: sdk: flutter - stream_chat_flutter: + stream_chat_flutter: path: ../ + stream_chat_persistence: + path: ../../stream_chat_persistence flutter_apns: ^1.4.1 flutter_local_notifications: ^2.0.2 flutter_svg: ^0.19.1 diff --git a/packages/stream_chat_persistence/lib/src/db/shared/unsupported_db.dart b/packages/stream_chat_persistence/lib/src/db/shared/unsupported_db.dart index 7415fdba..647314eb 100644 --- a/packages/stream_chat_persistence/lib/src/db/shared/unsupported_db.dart +++ b/packages/stream_chat_persistence/lib/src/db/shared/unsupported_db.dart @@ -11,7 +11,7 @@ class SharedDB { static constructOfflineStorage( String dbName, { - logStatements = false, + bool logStatements = false, }) { throw 'Unsupported Platform'; } diff --git a/packages/stream_chat_persistence/lib/src/mapper/channel_mapper.dart b/packages/stream_chat_persistence/lib/src/mapper/channel_mapper.dart index cdabf17f..4d35340b 100644 --- a/packages/stream_chat_persistence/lib/src/mapper/channel_mapper.dart +++ b/packages/stream_chat_persistence/lib/src/mapper/channel_mapper.dart @@ -1,5 +1,4 @@ import 'package:stream_chat/stream_chat.dart'; -import 'user_mapper.dart'; import 'package:stream_chat_persistence/src/db/moor_chat_database.dart'; /// diff --git a/packages/stream_chat_persistence/lib/src/stream_chat_persistence_impl.dart b/packages/stream_chat_persistence/lib/src/stream_chat_persistence_client.dart similarity index 79% rename from packages/stream_chat_persistence/lib/src/stream_chat_persistence_impl.dart rename to packages/stream_chat_persistence/lib/src/stream_chat_persistence_client.dart index 2d4caae8..72536b93 100644 --- a/packages/stream_chat_persistence/lib/src/stream_chat_persistence_impl.dart +++ b/packages/stream_chat_persistence/lib/src/stream_chat_persistence_client.dart @@ -3,18 +3,30 @@ import 'package:stream_chat/stream_chat.dart'; import 'db/moor_chat_database.dart'; import 'db/shared/shared_db.dart'; -/// -class StreamChatPersistenceImpl extends StreamChatPersistence { - /// - StreamChatPersistenceImpl( - this._userId, { - Logger logger, - }) : _logger = logger, - assert(_userId != null); +/// Various connection modes on which [StreamChatPersistenceClient] can work +enum ConnectionMode { + /// Connects the [StreamChatPersistenceClient] on a regular/default isolate + regular, + + /// Connects the [StreamChatPersistenceClient] on a background isolate + background, +} + +/// +class StreamChatPersistenceClient extends ChatPersistenceClient { + /// + StreamChatPersistenceClient({ + /// Connection mode on which the client will work + ConnectionMode connectionMode = ConnectionMode.regular, + Level logLevel = Level.WARNING, + }) : assert(connectionMode != null), + assert(logLevel != null), + _connectionMode = connectionMode, + _logger = Logger.detached('💽')..level = logLevel; - final String _userId; - final Logger _logger; MoorChatDatabase _db; + final Logger _logger; + final ConnectionMode _connectionMode; bool get _debugAssertConnected { assert(() { @@ -30,27 +42,22 @@ class StreamChatPersistenceImpl extends StreamChatPersistence { } @override - Future connect({ - bool connectBackground = false, - bool logStatements = false, - }) async { + Future connect(String name) async { if (_db != null) { throw Exception( 'An instance of StreamChatDatabase is already connected.\n' 'disconnect the previous instance before connecting again.', ); } - - final dbName = 'db_$_userId'; - if (connectBackground) { - _logger?.info('Connecting on background isolate'); - _db = await SharedDB.constructOfflineStorage( - dbName, - logStatements: logStatements, - ); - } else { - _logger?.info('Connecting on a regular isolate'); - _db = MoorChatDatabase(dbName, logStatements: logStatements); + switch (_connectionMode) { + case ConnectionMode.regular: + _logger.info('Connecting on a regular isolate'); + _db = MoorChatDatabase(name); + return; + case ConnectionMode.background: + _logger.info('Connecting on background isolate'); + _db = await SharedDB.constructOfflineStorage(name); + return; } } @@ -202,9 +209,9 @@ class StreamChatPersistenceImpl extends StreamChatPersistence { @override Future disconnect({bool flush = false}) async { if (_db != null) { - _logger?.info('Disconnecting'); + _logger.info('Disconnecting'); if (flush) { - _logger?.info('Flushing'); + _logger.info('Flushing'); await _db.batch((batch) { _db.allTables.forEach((table) { _db.delete(table).go(); diff --git a/packages/stream_chat_persistence/lib/stream_chat_persistence.dart b/packages/stream_chat_persistence/lib/stream_chat_persistence.dart index 3d58cb17..5f9aff5b 100644 --- a/packages/stream_chat_persistence/lib/stream_chat_persistence.dart +++ b/packages/stream_chat_persistence/lib/stream_chat_persistence.dart @@ -1,3 +1,3 @@ library stream_chat_persistence; -export 'src/stream_chat_persistence_impl.dart'; +export 'src/stream_chat_persistence_client.dart'; diff --git a/packages/stream_chat_persistence/pubspec.yaml b/packages/stream_chat_persistence/pubspec.yaml index 1ce6e604..a0c97c89 100644 --- a/packages/stream_chat_persistence/pubspec.yaml +++ b/packages/stream_chat_persistence/pubspec.yaml @@ -11,6 +11,7 @@ dependencies: moor: ^3.4.0 path: ^1.7.0 path_provider: ^1.6.27 + sqlite3_flutter_libs: ^0.3.0 stream_chat: path: ../dart_client