mirror of
https://github.com/bitwarden/android.git
synced 2024-12-26 02:48:29 +03:00
Improved BroadcastService and added try...catch on async void callbacks (#1917)
This commit is contained in:
parent
dbc1e5ea3e
commit
448cce38e1
12 changed files with 335 additions and 257 deletions
|
@ -99,12 +99,13 @@ namespace Bit.Droid
|
||||||
{
|
{
|
||||||
ServiceContainer.Register<INativeLogService>("nativeLogService", new AndroidLogService());
|
ServiceContainer.Register<INativeLogService>("nativeLogService", new AndroidLogService());
|
||||||
#if FDROID
|
#if FDROID
|
||||||
ServiceContainer.Register<ILogger>("logger", new StubLogger());
|
var logger = new StubLogger();
|
||||||
#elif DEBUG
|
#elif DEBUG
|
||||||
ServiceContainer.Register<ILogger>("logger", DebugLogger.Instance);
|
var logger = DebugLogger.Instance;
|
||||||
#else
|
#else
|
||||||
ServiceContainer.Register<ILogger>("logger", Logger.Instance);
|
var logger = Logger.Instance;
|
||||||
#endif
|
#endif
|
||||||
|
ServiceContainer.Register("logger", logger);
|
||||||
|
|
||||||
// Note: This might cause a race condition. Investigate more.
|
// Note: This might cause a race condition. Investigate more.
|
||||||
Task.Run(() =>
|
Task.Run(() =>
|
||||||
|
@ -124,7 +125,7 @@ namespace Bit.Droid
|
||||||
var documentsPath = System.Environment.GetFolderPath(System.Environment.SpecialFolder.Personal);
|
var documentsPath = System.Environment.GetFolderPath(System.Environment.SpecialFolder.Personal);
|
||||||
var liteDbStorage = new LiteDbStorageService(Path.Combine(documentsPath, "bitwarden.db"));
|
var liteDbStorage = new LiteDbStorageService(Path.Combine(documentsPath, "bitwarden.db"));
|
||||||
var localizeService = new LocalizeService();
|
var localizeService = new LocalizeService();
|
||||||
var broadcasterService = new BroadcasterService();
|
var broadcasterService = new BroadcasterService(logger);
|
||||||
var messagingService = new MobileBroadcasterMessagingService(broadcasterService);
|
var messagingService = new MobileBroadcasterMessagingService(broadcasterService);
|
||||||
var i18nService = new MobileI18nService(localizeService.GetCurrentCultureInfo());
|
var i18nService = new MobileI18nService(localizeService.GetCurrentCultureInfo());
|
||||||
var secureStorageService = new SecureStorageService();
|
var secureStorageService = new SecureStorageService();
|
||||||
|
|
|
@ -10,6 +10,7 @@ using Bit.App.Utilities.AccountManagement;
|
||||||
using Bit.Core.Abstractions;
|
using Bit.Core.Abstractions;
|
||||||
using Bit.Core.Enums;
|
using Bit.Core.Enums;
|
||||||
using Bit.Core.Models.Data;
|
using Bit.Core.Models.Data;
|
||||||
|
using Bit.Core.Services;
|
||||||
using Bit.Core.Utilities;
|
using Bit.Core.Utilities;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
using Xamarin.Forms.Xaml;
|
using Xamarin.Forms.Xaml;
|
||||||
|
@ -55,6 +56,8 @@ namespace Bit.App
|
||||||
|
|
||||||
Bootstrap();
|
Bootstrap();
|
||||||
_broadcasterService.Subscribe(nameof(App), async (message) =>
|
_broadcasterService.Subscribe(nameof(App), async (message) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (message.Command == "showDialog")
|
if (message.Command == "showDialog")
|
||||||
{
|
{
|
||||||
|
@ -137,6 +140,11 @@ namespace Bit.App
|
||||||
new NavigationPage(new RemoveMasterPasswordPage()));
|
new NavigationPage(new RemoveMasterPasswordPage()));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LoggerHelper.LogEvenIfCantBeResolved(ex);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -54,7 +54,7 @@ namespace Bit.App.Pages
|
||||||
{
|
{
|
||||||
_vm.AvatarImageSource = await GetAvatarImageSourceAsync();
|
_vm.AvatarImageSource = await GetAvatarImageSourceAsync();
|
||||||
}
|
}
|
||||||
_broadcasterService.Subscribe(nameof(HomePage), async (message) =>
|
_broadcasterService.Subscribe(nameof(HomePage), (message) =>
|
||||||
{
|
{
|
||||||
if (message.Command == "updatedTheme")
|
if (message.Command == "updatedTheme")
|
||||||
{
|
{
|
||||||
|
|
|
@ -5,6 +5,7 @@ using Bit.App.Controls;
|
||||||
using Bit.App.Models;
|
using Bit.App.Models;
|
||||||
using Bit.Core.Abstractions;
|
using Bit.Core.Abstractions;
|
||||||
using Bit.Core.Enums;
|
using Bit.Core.Enums;
|
||||||
|
using Bit.Core.Services;
|
||||||
using Bit.Core.Utilities;
|
using Bit.Core.Utilities;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
@ -67,6 +68,8 @@ namespace Bit.App.Pages
|
||||||
}
|
}
|
||||||
|
|
||||||
_broadcasterService.Subscribe(_pageName, async (message) =>
|
_broadcasterService.Subscribe(_pageName, async (message) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (message.Command == "syncStarted")
|
if (message.Command == "syncStarted")
|
||||||
{
|
{
|
||||||
|
@ -84,6 +87,11 @@ namespace Bit.App.Pages
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LoggerHelper.LogEvenIfCantBeResolved(ex);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await LoadOnAppearedAsync(_mainLayout, false, async () =>
|
await LoadOnAppearedAsync(_mainLayout, false, async () =>
|
||||||
|
|
|
@ -6,6 +6,7 @@ using Bit.App.Models;
|
||||||
using Bit.App.Utilities;
|
using Bit.App.Utilities;
|
||||||
using Bit.Core.Abstractions;
|
using Bit.Core.Abstractions;
|
||||||
using Bit.Core.Enums;
|
using Bit.Core.Enums;
|
||||||
|
using Bit.Core.Services;
|
||||||
using Bit.Core.Utilities;
|
using Bit.Core.Utilities;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
@ -54,6 +55,8 @@ namespace Bit.App.Pages
|
||||||
_vm.AvatarImageSource = await GetAvatarImageSourceAsync();
|
_vm.AvatarImageSource = await GetAvatarImageSourceAsync();
|
||||||
|
|
||||||
_broadcasterService.Subscribe(nameof(AutofillCiphersPage), async (message) =>
|
_broadcasterService.Subscribe(nameof(AutofillCiphersPage), async (message) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (message.Command == "syncStarted")
|
if (message.Command == "syncStarted")
|
||||||
{
|
{
|
||||||
|
@ -71,6 +74,11 @@ namespace Bit.App.Pages
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LoggerHelper.LogEvenIfCantBeResolved(ex);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await LoadOnAppearedAsync(_mainLayout, false, async () =>
|
await LoadOnAppearedAsync(_mainLayout, false, async () =>
|
||||||
|
|
|
@ -7,6 +7,7 @@ using Bit.App.Resources;
|
||||||
using Bit.Core.Abstractions;
|
using Bit.Core.Abstractions;
|
||||||
using Bit.Core.Enums;
|
using Bit.Core.Enums;
|
||||||
using Bit.Core.Models.Data;
|
using Bit.Core.Models.Data;
|
||||||
|
using Bit.Core.Services;
|
||||||
using Bit.Core.Utilities;
|
using Bit.Core.Utilities;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
@ -94,6 +95,8 @@ namespace Bit.App.Pages
|
||||||
}
|
}
|
||||||
|
|
||||||
_broadcasterService.Subscribe(_pageName, async (message) =>
|
_broadcasterService.Subscribe(_pageName, async (message) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (message.Command == "syncStarted")
|
if (message.Command == "syncStarted")
|
||||||
{
|
{
|
||||||
|
@ -111,6 +114,11 @@ namespace Bit.App.Pages
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LoggerHelper.LogEvenIfCantBeResolved(ex);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await LoadOnAppearedAsync(_mainLayout, false, async () =>
|
await LoadOnAppearedAsync(_mainLayout, false, async () =>
|
||||||
|
|
|
@ -3,6 +3,7 @@ using System.Collections.Generic;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using Bit.App.Resources;
|
using Bit.App.Resources;
|
||||||
using Bit.Core.Abstractions;
|
using Bit.Core.Abstractions;
|
||||||
|
using Bit.Core.Services;
|
||||||
using Bit.Core.Utilities;
|
using Bit.Core.Utilities;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
@ -55,6 +56,8 @@ namespace Bit.App.Pages
|
||||||
}
|
}
|
||||||
|
|
||||||
_broadcasterService.Subscribe(nameof(ViewPage), async (message) =>
|
_broadcasterService.Subscribe(nameof(ViewPage), async (message) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (message.Command == "syncStarted")
|
if (message.Command == "syncStarted")
|
||||||
{
|
{
|
||||||
|
@ -88,6 +91,11 @@ namespace Bit.App.Pages
|
||||||
_vm.SaveFileSelected(data.Item1, data.Item2);
|
_vm.SaveFileSelected(data.Item1, data.Item2);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LoggerHelper.LogEvenIfCantBeResolved(ex);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
await LoadOnAppearedAsync(_scrollView, true, async () =>
|
await LoadOnAppearedAsync(_scrollView, true, async () =>
|
||||||
{
|
{
|
||||||
|
|
|
@ -5,7 +5,8 @@ namespace Bit.Core.Abstractions
|
||||||
{
|
{
|
||||||
public interface IBroadcasterService
|
public interface IBroadcasterService
|
||||||
{
|
{
|
||||||
void Send(Message message, string id = null);
|
void Send(Message message);
|
||||||
|
void Send(Message message, string id);
|
||||||
void Subscribe(string id, Action<Message> messageCallback);
|
void Subscribe(string id, Action<Message> messageCallback);
|
||||||
void Unsubscribe(string id);
|
void Unsubscribe(string id);
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,24 +8,58 @@ namespace Bit.App.Services
|
||||||
{
|
{
|
||||||
public class BroadcasterService : IBroadcasterService
|
public class BroadcasterService : IBroadcasterService
|
||||||
{
|
{
|
||||||
|
private readonly ILogger _logger;
|
||||||
private readonly Dictionary<string, Action<Message>> _subscribers = new Dictionary<string, Action<Message>>();
|
private readonly Dictionary<string, Action<Message>> _subscribers = new Dictionary<string, Action<Message>>();
|
||||||
private object _myLock = new object();
|
private object _myLock = new object();
|
||||||
|
|
||||||
public void Send(Message message, string id = null)
|
public BroadcasterService(ILogger logger)
|
||||||
|
{
|
||||||
|
_logger = logger;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Send(Message message)
|
||||||
{
|
{
|
||||||
lock (_myLock)
|
lock (_myLock)
|
||||||
{
|
{
|
||||||
if (!string.IsNullOrWhiteSpace(id))
|
|
||||||
{
|
|
||||||
if (_subscribers.ContainsKey(id))
|
|
||||||
{
|
|
||||||
Task.Run(() => _subscribers[id].Invoke(message));
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
foreach (var sub in _subscribers)
|
foreach (var sub in _subscribers)
|
||||||
{
|
{
|
||||||
Task.Run(() => sub.Value.Invoke(message));
|
Task.Run(() =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
sub.Value(message);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.Exception(ex);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Send(Message message, string id)
|
||||||
|
{
|
||||||
|
if (string.IsNullOrWhiteSpace(id))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
lock (_myLock)
|
||||||
|
{
|
||||||
|
if (_subscribers.TryGetValue(id, out var action))
|
||||||
|
{
|
||||||
|
Task.Run(() =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
action(message);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.Exception(ex);
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -33,16 +67,9 @@ namespace Bit.App.Services
|
||||||
public void Subscribe(string id, Action<Message> messageCallback)
|
public void Subscribe(string id, Action<Message> messageCallback)
|
||||||
{
|
{
|
||||||
lock (_myLock)
|
lock (_myLock)
|
||||||
{
|
|
||||||
if (_subscribers.ContainsKey(id))
|
|
||||||
{
|
{
|
||||||
_subscribers[id] = messageCallback;
|
_subscribers[id] = messageCallback;
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
_subscribers.Add(id, messageCallback);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Unsubscribe(string id)
|
public void Unsubscribe(string id)
|
||||||
|
|
|
@ -21,7 +21,7 @@ namespace Bit.iOS.Core.Renderers
|
||||||
public CustomTabbedRenderer()
|
public CustomTabbedRenderer()
|
||||||
{
|
{
|
||||||
_broadcasterService = ServiceContainer.Resolve<IBroadcasterService>("broadcasterService");
|
_broadcasterService = ServiceContainer.Resolve<IBroadcasterService>("broadcasterService");
|
||||||
_broadcasterService.Subscribe(nameof(CustomTabbedRenderer), async (message) =>
|
_broadcasterService.Subscribe(nameof(CustomTabbedRenderer), (message) =>
|
||||||
{
|
{
|
||||||
if (message.Command == "updatedTheme")
|
if (message.Command == "updatedTheme")
|
||||||
{
|
{
|
||||||
|
|
|
@ -38,13 +38,15 @@ namespace Bit.iOS.Core.Utilities
|
||||||
ServiceContainer.Register<INativeLogService>("nativeLogService", new ConsoleLogService());
|
ServiceContainer.Register<INativeLogService>("nativeLogService", new ConsoleLogService());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ILogger logger = null;
|
||||||
if (ServiceContainer.Resolve<ILogger>("logger", true) == null)
|
if (ServiceContainer.Resolve<ILogger>("logger", true) == null)
|
||||||
{
|
{
|
||||||
#if DEBUG
|
#if DEBUG
|
||||||
ServiceContainer.Register<ILogger>("logger", DebugLogger.Instance);
|
logger = DebugLogger.Instance;
|
||||||
#else
|
#else
|
||||||
ServiceContainer.Register<ILogger>("logger", Logger.Instance);
|
logger = Logger.Instance;
|
||||||
#endif
|
#endif
|
||||||
|
ServiceContainer.Register("logger", logger);
|
||||||
}
|
}
|
||||||
|
|
||||||
var preferencesStorage = new PreferencesStorageService(AppGroupId);
|
var preferencesStorage = new PreferencesStorageService(AppGroupId);
|
||||||
|
@ -52,7 +54,7 @@ namespace Bit.iOS.Core.Utilities
|
||||||
var liteDbStorage = new LiteDbStorageService(
|
var liteDbStorage = new LiteDbStorageService(
|
||||||
Path.Combine(appGroupContainer.Path, "Library", "bitwarden.db"));
|
Path.Combine(appGroupContainer.Path, "Library", "bitwarden.db"));
|
||||||
var localizeService = new LocalizeService();
|
var localizeService = new LocalizeService();
|
||||||
var broadcasterService = new BroadcasterService();
|
var broadcasterService = new BroadcasterService(logger);
|
||||||
var messagingService = new MobileBroadcasterMessagingService(broadcasterService);
|
var messagingService = new MobileBroadcasterMessagingService(broadcasterService);
|
||||||
var i18nService = new MobileI18nService(localizeService.GetCurrentCultureInfo());
|
var i18nService = new MobileI18nService(localizeService.GetCurrentCultureInfo());
|
||||||
var secureStorageService = new KeyChainStorageService(AppId, AccessGroup,
|
var secureStorageService = new KeyChainStorageService(AppId, AccessGroup,
|
||||||
|
|
|
@ -58,6 +58,8 @@ namespace Bit.iOS
|
||||||
ZXing.Net.Mobile.Forms.iOS.Platform.Init();
|
ZXing.Net.Mobile.Forms.iOS.Platform.Init();
|
||||||
|
|
||||||
_broadcasterService.Subscribe(nameof(AppDelegate), async (message) =>
|
_broadcasterService.Subscribe(nameof(AppDelegate), async (message) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (message.Command == "startEventTimer")
|
if (message.Command == "startEventTimer")
|
||||||
{
|
{
|
||||||
|
@ -168,6 +170,11 @@ namespace Bit.iOS
|
||||||
await ASHelpers.ReplaceAllIdentities();
|
await ASHelpers.ReplaceAllIdentities();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
LoggerHelper.LogEvenIfCantBeResolved(ex);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return base.FinishedLaunching(app, options);
|
return base.FinishedLaunching(app, options);
|
||||||
|
|
Loading…
Reference in a new issue