mirror of
https://github.com/bitwarden/android.git
synced 2025-03-14 02:08:48 +03:00
Fixes for iOS push notifications (#1708)
* WIP Fixes for iOS push notifications * WIP Fixes for iOS push notifications, fix missed implementation on android * Fix some issues on the push notifications, changed to Debug Console.WriteLine, and added update on entitlements on the build.yml
This commit is contained in:
parent
42403210a0
commit
2791d4b8ec
8 changed files with 107 additions and 31 deletions
9
.github/workflows/build.yml
vendored
9
.github/workflows/build.yml
vendored
|
@ -397,6 +397,15 @@ jobs:
|
|||
perl -0777 -pi.bak -e 's/<key>CFBundleVersion<\/key>\s*<string>1<\/string>/<key>CFBundleVersion<\/key>\n\t<string>'"$BUILD_NUMBER"'<\/string>/' ./src/iOS.Autofill/Info.plist
|
||||
shell: bash
|
||||
|
||||
- name: Update Entitlements
|
||||
run: |
|
||||
echo "########################################"
|
||||
echo "##### Updating Entitlements"
|
||||
echo "########################################"
|
||||
|
||||
perl -0777 -pi.bak -e 's/<key>aps-environment<\/key>\s*<string>development<\/string>/<key>aps-environment<\/key>\n\t<string>production<\/string>/' ./src/iOS/Entitlements.plist
|
||||
shell: bash
|
||||
|
||||
- name: Set up Keychain
|
||||
env:
|
||||
KEYCHAIN_PASSWORD: ${{ secrets.IOS_KEYCHAIN_PASSWORD }}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#if !FDROID
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using AndroidX.Core.App;
|
||||
using Bit.App.Abstractions;
|
||||
using Bit.Core;
|
||||
using Bit.Core.Abstractions;
|
||||
|
@ -21,6 +22,8 @@ namespace Bit.Droid.Services
|
|||
_pushNotificationListenerService = pushNotificationListenerService;
|
||||
}
|
||||
|
||||
public bool IsRegisteredForPush => NotificationManagerCompat.From(Android.App.Application.Context)?.AreNotificationsEnabled() ?? false;
|
||||
|
||||
public async Task<string> GetTokenAsync()
|
||||
{
|
||||
return await _storageService.GetAsync<string>(Constants.PushCurrentTokenKey);
|
||||
|
|
|
@ -4,6 +4,7 @@ namespace Bit.App.Abstractions
|
|||
{
|
||||
public interface IPushNotificationService
|
||||
{
|
||||
bool IsRegisteredForPush { get; }
|
||||
Task<string> GetTokenAsync();
|
||||
Task RegisterAsync();
|
||||
Task UnregisterAsync();
|
||||
|
|
|
@ -1,15 +1,14 @@
|
|||
using Bit.App.Abstractions;
|
||||
using Bit.App.Models;
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using Bit.App.Abstractions;
|
||||
using Bit.App.Resources;
|
||||
using Bit.App.Utilities;
|
||||
using Bit.Core;
|
||||
using Bit.Core.Abstractions;
|
||||
using Bit.Core.Enums;
|
||||
using Bit.Core.Models.Domain;
|
||||
using Bit.Core.Utilities;
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using Bit.App.Utilities;
|
||||
using Bit.Core.Models.Request;
|
||||
using Bit.Core.Utilities;
|
||||
using Xamarin.Forms;
|
||||
|
||||
namespace Bit.App.Pages
|
||||
|
@ -135,7 +134,7 @@ namespace Bit.App.Pages
|
|||
|
||||
// Users with key connector and without biometric or pin has no MP to unlock with
|
||||
_usingKeyConnector = await _keyConnectorService.GetUsesKeyConnector();
|
||||
if ( _usingKeyConnector && !(BiometricLock || PinLock))
|
||||
if (_usingKeyConnector && !(BiometricLock || PinLock))
|
||||
{
|
||||
await _vaultTimeoutService.LogOutAsync();
|
||||
}
|
||||
|
|
|
@ -5,6 +5,8 @@ namespace Bit.App.Services
|
|||
{
|
||||
public class NoopPushNotificationService : IPushNotificationService
|
||||
{
|
||||
public bool IsRegisteredForPush => false;
|
||||
|
||||
public Task<string> GetTokenAsync()
|
||||
{
|
||||
return Task.FromResult(null as string);
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
|
@ -25,5 +25,7 @@
|
|||
<array>
|
||||
<string>webcredentials:bitwarden.com</string>
|
||||
</array>
|
||||
<key>aps-environment</key>
|
||||
<string>development</string>
|
||||
</dict>
|
||||
</plist>
|
||||
|
|
|
@ -1,13 +1,15 @@
|
|||
using Bit.App.Abstractions;
|
||||
using Foundation;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using System;
|
||||
using System;
|
||||
using System.Diagnostics;
|
||||
using Bit.App.Abstractions;
|
||||
using Foundation;
|
||||
using Microsoft.AppCenter.Crashes;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using UserNotifications;
|
||||
using Xamarin.Forms;
|
||||
|
||||
namespace Bit.iOS.Services
|
||||
{
|
||||
public class iOSPushNotificationHandler
|
||||
public class iOSPushNotificationHandler : NSObject, IUNUserNotificationCenterDelegate
|
||||
{
|
||||
private const string TokenSetting = "token";
|
||||
private const string DomainName = "iOSPushNotificationService";
|
||||
|
@ -22,20 +24,27 @@ namespace Bit.iOS.Services
|
|||
|
||||
public void OnMessageReceived(NSDictionary userInfo)
|
||||
{
|
||||
var json = DictionaryToJson(userInfo);
|
||||
var values = JObject.Parse(json);
|
||||
var keyAps = new NSString("aps");
|
||||
if (userInfo.ContainsKey(keyAps) && userInfo.ValueForKey(keyAps) is NSDictionary aps)
|
||||
try
|
||||
{
|
||||
foreach (var apsKey in aps)
|
||||
var json = DictionaryToJson(userInfo);
|
||||
var values = JObject.Parse(json);
|
||||
var keyAps = new NSString("aps");
|
||||
if (userInfo.ContainsKey(keyAps) && userInfo.ValueForKey(keyAps) is NSDictionary aps)
|
||||
{
|
||||
if (!values.TryGetValue(apsKey.Key.ToString(), out JToken temp))
|
||||
foreach (var apsKey in aps)
|
||||
{
|
||||
values.Add(apsKey.Key.ToString(), apsKey.Value.ToString());
|
||||
if (!values.TryGetValue(apsKey.Key.ToString(), out JToken temp))
|
||||
{
|
||||
values.Add(apsKey.Key.ToString(), apsKey.Value.ToString());
|
||||
}
|
||||
}
|
||||
}
|
||||
_pushNotificationListenerService.OnMessageAsync(values, Device.iOS);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Crashes.TrackError(ex);
|
||||
}
|
||||
_pushNotificationListenerService.OnMessageAsync(values, Device.iOS);
|
||||
}
|
||||
|
||||
public void OnErrorReceived(NSError error)
|
||||
|
@ -47,9 +56,15 @@ namespace Bit.iOS.Services
|
|||
public void OnRegisteredSuccess(NSData token)
|
||||
{
|
||||
Debug.WriteLine("{0} - Successfully Registered.", DomainName);
|
||||
|
||||
var hexDeviceToken = BitConverter.ToString(token.ToArray())
|
||||
.Replace("-", string.Empty).ToLowerInvariant();
|
||||
Console.WriteLine("{0} - Token: {1}", DomainName, hexDeviceToken);
|
||||
.Replace("-", string.Empty)
|
||||
.ToLowerInvariant();
|
||||
|
||||
Debug.WriteLine("{0} - Token: {1}", DomainName, hexDeviceToken);
|
||||
|
||||
UNUserNotificationCenter.Current.Delegate = this;
|
||||
|
||||
_pushNotificationListenerService.OnRegisteredAsync(hexDeviceToken, Device.iOS);
|
||||
NSUserDefaults.StandardUserDefaults.SetString(hexDeviceToken, TokenSetting);
|
||||
NSUserDefaults.StandardUserDefaults.Synchronize();
|
||||
|
@ -60,5 +75,29 @@ namespace Bit.iOS.Services
|
|||
var json = NSJsonSerialization.Serialize(dictionary, NSJsonWritingOptions.PrettyPrinted, out NSError error);
|
||||
return json.ToString(NSStringEncoding.UTF8);
|
||||
}
|
||||
|
||||
// To receive notifications in foreground on iOS 10 devices.
|
||||
[Export("userNotificationCenter:willPresentNotification:withCompletionHandler:")]
|
||||
public void WillPresentNotification(UNUserNotificationCenter center, UNNotification notification, Action<UNNotificationPresentationOptions> completionHandler)
|
||||
{
|
||||
Debug.WriteLine($"{DomainName} WillPresentNotification {notification?.Request?.Content?.UserInfo}");
|
||||
|
||||
OnMessageReceived(notification?.Request?.Content?.UserInfo);
|
||||
completionHandler(UNNotificationPresentationOptions.Alert);
|
||||
}
|
||||
|
||||
[Export("userNotificationCenter:didReceiveNotificationResponse:withCompletionHandler:")]
|
||||
public void DidReceiveNotificationResponse(UNUserNotificationCenter center, UNNotificationResponse response, Action completionHandler)
|
||||
{
|
||||
Debug.WriteLine($"{DomainName} DidReceiveNotificationResponse {response?.Notification?.Request?.Content?.UserInfo}");
|
||||
|
||||
if (response.IsDefaultAction)
|
||||
{
|
||||
OnMessageReceived(response?.Notification?.Request?.Content?.UserInfo);
|
||||
}
|
||||
|
||||
// Inform caller it has been handled
|
||||
completionHandler();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,11 +1,14 @@
|
|||
using System.Threading.Tasks;
|
||||
using System;
|
||||
using System.Diagnostics;
|
||||
using System.Threading.Tasks;
|
||||
using Bit.App.Abstractions;
|
||||
using Foundation;
|
||||
using UIKit;
|
||||
using UserNotifications;
|
||||
|
||||
namespace Bit.iOS.Services
|
||||
{
|
||||
public class iOSPushNotificationService : IPushNotificationService
|
||||
public class iOSPushNotificationService : NSObject, IPushNotificationService, IUNUserNotificationCenterDelegate
|
||||
{
|
||||
private const string TokenSetting = "token";
|
||||
|
||||
|
@ -14,13 +17,31 @@ namespace Bit.iOS.Services
|
|||
return Task.FromResult(NSUserDefaults.StandardUserDefaults.StringForKey(TokenSetting));
|
||||
}
|
||||
|
||||
public Task RegisterAsync()
|
||||
public bool IsRegisteredForPush => UIApplication.SharedApplication.IsRegisteredForRemoteNotifications;
|
||||
|
||||
public async Task RegisterAsync()
|
||||
{
|
||||
var userNotificationTypes = UIUserNotificationType.Alert | UIUserNotificationType.Badge |
|
||||
UIUserNotificationType.Sound;
|
||||
var settings = UIUserNotificationSettings.GetSettingsForTypes(userNotificationTypes, null);
|
||||
UIApplication.SharedApplication.RegisterUserNotificationSettings(settings);
|
||||
return Task.FromResult(0);
|
||||
var tcs = new TaskCompletionSource<bool>();
|
||||
|
||||
var authOptions = UNAuthorizationOptions.Alert | UNAuthorizationOptions.Badge | UNAuthorizationOptions.Sound;
|
||||
UNUserNotificationCenter.Current.RequestAuthorization(authOptions, (granted, error) =>
|
||||
{
|
||||
if (error != null)
|
||||
{
|
||||
Debug.WriteLine($"Push Notifications {error}");
|
||||
}
|
||||
else
|
||||
{
|
||||
Debug.WriteLine($"Push Notifications {granted}");
|
||||
}
|
||||
|
||||
tcs.SetResult(granted);
|
||||
});
|
||||
|
||||
if (await tcs.Task)
|
||||
{
|
||||
UIApplication.SharedApplication.RegisterForRemoteNotifications();
|
||||
}
|
||||
}
|
||||
|
||||
public Task UnregisterAsync()
|
||||
|
|
Loading…
Add table
Reference in a new issue