APNS LaunchPad
This commit is contained in:
20
MIT-LICENSE
Normal file
20
MIT-LICENSE
Normal file
@@ -0,0 +1,20 @@
|
||||
Copyright 2012-2017 Adobe Systems
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of this software and associated documentation files (the
|
||||
"Software"), to deal in the Software without restriction, including
|
||||
without limitation the rights to use, copy, modify, merge, publish,
|
||||
distribute, sublicense, and/or sell copies of the Software, and to
|
||||
permit persons to whom the Software is furnished to do so, subject to
|
||||
the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be
|
||||
included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
52
README.md
52
README.md
@@ -1,2 +1,52 @@
|
||||
# cordova-plugin-apns-push
|
||||
APNS only push plugin | Alpha release
|
||||
|
||||
> Register and receive APNS push notifications
|
||||
|
||||
# Usage
|
||||
|
||||
```js
|
||||
|
||||
var push = window['APNSPushNotification'].init({
|
||||
ios: {
|
||||
alert: "true",
|
||||
badge: "true",
|
||||
sound: "true"
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
push.on('registration', (data) => {
|
||||
// data.registrationId
|
||||
this.sendRegDetails(data.registrationId);
|
||||
});
|
||||
|
||||
push.on('notification', (data) => {
|
||||
window['cordova'].plugins.notification.local.schedule({
|
||||
title: data.title,
|
||||
text: data.message,
|
||||
sound: data.sound,
|
||||
at: new Date().getTime()
|
||||
});
|
||||
});
|
||||
|
||||
push.on('error', (e) => {
|
||||
// e.message
|
||||
console.error(e);
|
||||
});
|
||||
|
||||
```
|
||||
|
||||
# Supported Platforms
|
||||
|
||||
- iOS
|
||||
|
||||
# More about us
|
||||
Find out more or contact us directly here :- http://www.neutrinos.co/
|
||||
|
||||
Facebook :- https://www.facebook.com/Neutrinos.co/ <br/>
|
||||
LinkedIn :- https://www.linkedin.com/company/25057297/ <br/>
|
||||
Twitter :- https://twitter.com/Neutrinosco <br/>
|
||||
Instagram :- https://www.instagram.com/neutrinos.co/
|
||||
|
||||
[](http://www.neutrinos.co/)
|
||||
|
||||
|
||||
31
package.json
Normal file
31
package.json
Normal file
@@ -0,0 +1,31 @@
|
||||
{
|
||||
"name": "cordova-plugin-apns-push",
|
||||
"description": "Register and receive APNS push notifications.",
|
||||
"version": "1.0.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/NeutrinosPlatform/cordova-plugin-apns-push"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/NeutrinosPlatform/cordova-plugin-apns-push/issues"
|
||||
},
|
||||
"cordova": {
|
||||
"id": "cordova-plugin-apns-push",
|
||||
"platforms": [
|
||||
"ios"
|
||||
]
|
||||
},
|
||||
"keywords": [
|
||||
"ecosystem:cordova",
|
||||
"ecosystem:phonegap",
|
||||
"cordova-ios"
|
||||
],
|
||||
"engines": {
|
||||
"cordovaDependencies": {
|
||||
"cordova": ">=7.1.0",
|
||||
"cordova-ios": ">=4.5.0"
|
||||
}
|
||||
},
|
||||
"author": "jatahworx",
|
||||
"license": "MIT"
|
||||
}
|
||||
41
plugin.xml
Normal file
41
plugin.xml
Normal file
@@ -0,0 +1,41 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<plugin xmlns="http://www.phonegap.com/ns/plugins/1.0"
|
||||
id="cordova-plugin-apns-push"
|
||||
version="1.0.0">
|
||||
|
||||
<name>APNSPushPlugin</name>
|
||||
<description> This plugin allows your application to receive apple push notifications (APNS) on iOS devices. </description>
|
||||
<license>MIT</license>
|
||||
<js-module src="www/apnspush.js" name="APNSPushNotification">
|
||||
<clobbers target="APNSPushNotification"/>
|
||||
</js-module>
|
||||
<engines>
|
||||
<engine name="cordova" version=">=7.1.0"/>
|
||||
<engine name="cordova-ios" version=">=4.5.0"/>
|
||||
</engines>
|
||||
|
||||
<platform name="ios">
|
||||
<config-file target="config.xml" parent="/*">
|
||||
<feature name="APNSPushNotification">
|
||||
<param name="ios-package" value="PushPlugin"/>
|
||||
</feature>
|
||||
</config-file>
|
||||
<config-file target="*-Info.plist" parent="UIBackgroundModes">
|
||||
<array>
|
||||
<string>remote-notification</string>
|
||||
</array>
|
||||
</config-file>
|
||||
<config-file target="*-Debug.plist" parent="aps-environment">
|
||||
<string>development</string>
|
||||
</config-file>
|
||||
<config-file target="*-Release.plist" parent="aps-environment">
|
||||
<string>production</string>
|
||||
</config-file>
|
||||
<source-file src="src/ios/AppDelegate+apnsnotification.m"/>
|
||||
<source-file src="src/ios/APNSPushPlugin.m"/>
|
||||
<header-file src="src/ios/AppDelegate+apnsnotification.h"/>
|
||||
<header-file src="src/ios/APNSPushPlugin.h"/>
|
||||
<framework src="PushKit.framework"/>
|
||||
</platform>
|
||||
|
||||
</plugin>
|
||||
86
src/ios/APNSPushPlugin.h
Normal file
86
src/ios/APNSPushPlugin.h
Normal file
@@ -0,0 +1,86 @@
|
||||
/*
|
||||
Copyright 2009-2011 Urban Airship Inc. All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
|
||||
1. Redistributions of source code must retain the above copyright notice, this
|
||||
list of conditions and the following disclaimer.
|
||||
|
||||
2. Redistributions in binaryform must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided withthe distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE URBAN AIRSHIP INC``AS IS'' AND ANY EXPRESS OR
|
||||
IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
|
||||
EVENT SHALL URBAN AIRSHIP INC OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
@import Foundation;
|
||||
@import UserNotifications;
|
||||
#import <Cordova/CDV.h>
|
||||
#import <Cordova/CDVPlugin.h>
|
||||
#import <PushKit/PushKit.h>
|
||||
|
||||
@protocol GGLInstanceIDDelegate;
|
||||
@protocol GCMReceiverDelegate;
|
||||
@interface PushPlugin : CDVPlugin
|
||||
{
|
||||
NSDictionary *notificationMessage;
|
||||
BOOL isInline;
|
||||
NSString *notificationCallbackId;
|
||||
NSString *callback;
|
||||
BOOL clearBadge;
|
||||
|
||||
NSMutableDictionary *handlerObj;
|
||||
void (^completionHandler)(UIBackgroundFetchResult);
|
||||
|
||||
BOOL ready;
|
||||
}
|
||||
|
||||
@property (nonatomic, copy) NSString *callbackId;
|
||||
@property (nonatomic, copy) NSString *notificationCallbackId;
|
||||
@property (nonatomic, copy) NSString *callback;
|
||||
|
||||
@property (nonatomic, strong) NSDictionary *notificationMessage;
|
||||
@property BOOL isInline;
|
||||
@property BOOL coldstart;
|
||||
@property BOOL clearBadge;
|
||||
@property (nonatomic, strong) NSMutableDictionary *handlerObj;
|
||||
|
||||
- (void)init:(CDVInvokedUrlCommand*)command;
|
||||
- (void)unregister:(CDVInvokedUrlCommand*)command;
|
||||
- (void)subscribe:(CDVInvokedUrlCommand*)command;
|
||||
- (void)unsubscribe:(CDVInvokedUrlCommand*)command;
|
||||
- (void)clearNotification:(CDVInvokedUrlCommand*)command;
|
||||
|
||||
- (void)didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken;
|
||||
- (void)didFailToRegisterForRemoteNotificationsWithError:(NSError *)error;
|
||||
|
||||
- (void)setNotificationMessage:(NSDictionary *)notification;
|
||||
- (void)notificationReceived;
|
||||
|
||||
- (void)willSendDataMessageWithID:(NSString *)messageID error:(NSError *)error;
|
||||
- (void)didSendDataMessageWithID:(NSString *)messageID;
|
||||
- (void)didDeleteMessagesOnServer;
|
||||
|
||||
// VoIP Features
|
||||
- (void)pushRegistry:(PKPushRegistry *)registry didUpdatePushCredentials:(PKPushCredentials *)credentials forType:(NSString *)type;
|
||||
- (void)pushRegistry:(PKPushRegistry *)registry didReceiveIncomingPushWithPayload:(PKPushPayload *)payload forType:(NSString *)type;
|
||||
|
||||
// FCM Features
|
||||
@property(nonatomic, assign) BOOL usesFCM;
|
||||
@property(nonatomic, strong) NSNumber *fcmSandbox;
|
||||
@property(nonatomic, strong) NSString *fcmSenderId;
|
||||
@property(nonatomic, strong) NSDictionary *fcmRegistrationOptions;
|
||||
@property(nonatomic, strong) NSString *fcmRegistrationToken;
|
||||
@property(nonatomic, strong) NSArray *fcmTopics;
|
||||
|
||||
@end
|
||||
646
src/ios/APNSPushPlugin.m
Normal file
646
src/ios/APNSPushPlugin.m
Normal file
@@ -0,0 +1,646 @@
|
||||
/*
|
||||
Copyright 2009-2011 Urban Airship Inc. All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
|
||||
1. Redistributions of source code must retain the above copyright notice, this
|
||||
list of conditions and the following disclaimer.
|
||||
|
||||
2. Redistributions in binaryform must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided withthe distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE URBAN AIRSHIP INC``AS IS'' AND ANY EXPRESS OR
|
||||
IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
|
||||
EVENT SHALL URBAN AIRSHIP INC OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
// See GGLInstanceID.h
|
||||
#define GMP_NO_MODULES true
|
||||
|
||||
#import "APNSPushPlugin.h"
|
||||
#import "AppDelegate+apnsnotification.h"
|
||||
|
||||
|
||||
@implementation PushPlugin : CDVPlugin
|
||||
|
||||
@synthesize notificationMessage;
|
||||
@synthesize isInline;
|
||||
@synthesize coldstart;
|
||||
|
||||
@synthesize callbackId;
|
||||
@synthesize notificationCallbackId;
|
||||
@synthesize callback;
|
||||
@synthesize clearBadge;
|
||||
@synthesize handlerObj;
|
||||
|
||||
@synthesize usesFCM;
|
||||
@synthesize fcmSandbox;
|
||||
@synthesize fcmSenderId;
|
||||
@synthesize fcmRegistrationOptions;
|
||||
@synthesize fcmRegistrationToken;
|
||||
@synthesize fcmTopics;
|
||||
|
||||
//////////////////////////////////=====================
|
||||
//-(void)initRegistration;
|
||||
//{
|
||||
// NSString * registrationToken = [[FIRInstanceID instanceID] token];
|
||||
//
|
||||
// if (registrationToken != nil) {
|
||||
// NSLog(@"FCM Registration Token: %@", registrationToken);
|
||||
// [self setFcmRegistrationToken: registrationToken];
|
||||
//
|
||||
// id topics = [self fcmTopics];
|
||||
// if (topics != nil) {
|
||||
// for (NSString *topic in topics) {
|
||||
// NSLog(@"subscribe to topic: %@", topic);
|
||||
// id pubSub = [FIRMessaging messaging];
|
||||
// [pubSub subscribeToTopic:topic];
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// [self registerWithToken:registrationToken];
|
||||
// } else {
|
||||
// NSLog(@"FCM token is null");
|
||||
// }
|
||||
//
|
||||
//}
|
||||
|
||||
// FCM refresh token
|
||||
// Unclear how this is testable under normal circumstances
|
||||
|
||||
/////////////////////////////////=====================
|
||||
//- (void)onTokenRefresh {
|
||||
//#if !TARGET_IPHONE_SIMULATOR
|
||||
// // A rotation of the registration tokens is happening, so the app needs to request a new token.
|
||||
// NSLog(@"The FCM registration token needs to be changed.");
|
||||
// [[FIRInstanceID instanceID] token];
|
||||
// [self initRegistration];
|
||||
//#endif
|
||||
//}
|
||||
|
||||
// contains error info
|
||||
- (void)sendDataMessageFailure:(NSNotification *)notification {
|
||||
NSLog(@"sendDataMessageFailure");
|
||||
}
|
||||
- (void)sendDataMessageSuccess:(NSNotification *)notification {
|
||||
NSLog(@"sendDataMessageSuccess");
|
||||
}
|
||||
|
||||
- (void)didSendDataMessageWithID:messageID {
|
||||
NSLog(@"didSendDataMessageWithID");
|
||||
}
|
||||
|
||||
- (void)willSendDataMessageWithID:messageID error:error {
|
||||
NSLog(@"willSendDataMessageWithID");
|
||||
}
|
||||
|
||||
- (void)didDeleteMessagesOnServer {
|
||||
NSLog(@"didDeleteMessagesOnServer");
|
||||
// Some messages sent to this device were deleted on the GCM server before reception, likely
|
||||
// because the TTL expired. The client should notify the app server of this, so that the app
|
||||
// server can resend those messages.
|
||||
}
|
||||
|
||||
/////////////////////////////////=====================
|
||||
- (void)unregister:(CDVInvokedUrlCommand*)command;
|
||||
{
|
||||
NSArray* topics = [command argumentAtIndex:0];
|
||||
|
||||
if (topics != nil) {
|
||||
/////////////////////////////////=====================id pubSub = [FIRMessaging messaging];
|
||||
for (NSString *topic in topics) {
|
||||
NSLog(@"unsubscribe from topic: %@", topic);
|
||||
/////////////////////////////////=====================[pubSub unsubscribeFromTopic:topic];
|
||||
}
|
||||
} else {
|
||||
[[UIApplication sharedApplication] unregisterForRemoteNotifications];
|
||||
[self successWithMessage:command.callbackId withMsg:@"unregistered"];
|
||||
}
|
||||
}
|
||||
|
||||
- (void)subscribe:(CDVInvokedUrlCommand*)command;
|
||||
{
|
||||
NSString* topic = [command argumentAtIndex:0];
|
||||
|
||||
if (topic != nil) {
|
||||
NSLog(@"subscribe from topic: %@", topic);
|
||||
/////////////////////////////////=====================id pubSub = [FIRMessaging messaging];
|
||||
/////////////////////////////////=====================[pubSub subscribeToTopic:topic];
|
||||
NSLog(@"Successfully subscribe to topic %@", topic);
|
||||
[self successWithMessage:command.callbackId withMsg:[NSString stringWithFormat:@"Successfully subscribe to topic %@", topic]];
|
||||
} else {
|
||||
NSLog(@"There is no topic to subscribe");
|
||||
[self successWithMessage:command.callbackId withMsg:@"There is no topic to subscribe"];
|
||||
}
|
||||
}
|
||||
|
||||
- (void)unsubscribe:(CDVInvokedUrlCommand*)command;
|
||||
{
|
||||
NSString* topic = [command argumentAtIndex:0];
|
||||
|
||||
if (topic != nil) {
|
||||
NSLog(@"unsubscribe from topic: %@", topic);
|
||||
/////////////////////////////////=====================id pubSub = [FIRMessaging messaging];
|
||||
/////////////////////////////////=====================[pubSub unsubscribeFromTopic:topic];
|
||||
NSLog(@"Successfully unsubscribe from topic %@", topic);
|
||||
[self successWithMessage:command.callbackId withMsg:[NSString stringWithFormat:@"Successfully unsubscribe from topic %@", topic]];
|
||||
} else {
|
||||
NSLog(@"There is no topic to unsubscribe");
|
||||
[self successWithMessage:command.callbackId withMsg:@"There is no topic to unsubscribe"];
|
||||
}
|
||||
}
|
||||
|
||||
- (void)init:(CDVInvokedUrlCommand*)command;
|
||||
{
|
||||
NSMutableDictionary* options = [command.arguments objectAtIndex:0];
|
||||
NSMutableDictionary* iosOptions = [options objectForKey:@"ios"];
|
||||
BOOL apnsForce = false;
|
||||
id apnsForceArg = [iosOptions objectForKey:@"apnsForce"];
|
||||
if (([apnsForceArg isKindOfClass:[NSString class]] && [apnsForceArg isEqualToString:@"true"]) || [apnsForceArg boolValue]) {
|
||||
apnsForce = true;
|
||||
NSLog(@"Push Plugin will now use APNS even if GoogleService-Info.plist is present");
|
||||
}
|
||||
id voipArg = [iosOptions objectForKey:@"voip"];
|
||||
if (([voipArg isKindOfClass:[NSString class]] && [voipArg isEqualToString:@"true"]) || [voipArg boolValue]) {
|
||||
[self.commandDelegate runInBackground:^ {
|
||||
NSLog(@"Push Plugin VoIP set to true");
|
||||
|
||||
self.callbackId = command.callbackId;
|
||||
|
||||
PKPushRegistry *pushRegistry = [[PKPushRegistry alloc] initWithQueue:dispatch_get_main_queue()];
|
||||
pushRegistry.delegate = self;
|
||||
pushRegistry.desiredPushTypes = [NSSet setWithObject:PKPushTypeVoIP];
|
||||
}];
|
||||
} else {
|
||||
NSLog(@"Push Plugin VoIP missing or false");
|
||||
/////////////////////////////////=====================[[NSNotificationCenter defaultCenter]
|
||||
/////////////////////////////////=====================addObserver:self selector:@selector(onTokenRefresh)
|
||||
/////////////////////////////////=====================name:kFIRInstanceIDTokenRefreshNotification object:nil];
|
||||
|
||||
/////////////////////////////////=====================[[NSNotificationCenter defaultCenter]
|
||||
/////////////////////////////////=====================addObserver:self selector:@selector(sendDataMessageFailure:)
|
||||
/////////////////////////////////=====================name:FIRMessagingSendErrorNotification object:nil];
|
||||
|
||||
/////////////////////////////////=====================[[NSNotificationCenter defaultCenter]
|
||||
/////////////////////////////////=====================addObserver:self selector:@selector(sendDataMessageSuccess:)
|
||||
/////////////////////////////////=====================name:FIRMessagingSendSuccessNotification object:nil];
|
||||
|
||||
/////////////////////////////////=====================[[NSNotificationCenter defaultCenter]
|
||||
/////////////////////////////////=====================addObserver:self selector:@selector(didDeleteMessagesOnServer)
|
||||
/////////////////////////////////=====================name:FIRMessagingMessagesDeletedNotification object:nil];
|
||||
|
||||
[self.commandDelegate runInBackground:^ {
|
||||
NSLog(@"Push Plugin register called");
|
||||
self.callbackId = command.callbackId;
|
||||
|
||||
NSArray* topics = [iosOptions objectForKey:@"topics"];
|
||||
[self setFcmTopics:topics];
|
||||
|
||||
UNAuthorizationOptions authorizationOptions = UNAuthorizationOptionNone;
|
||||
|
||||
id badgeArg = [iosOptions objectForKey:@"badge"];
|
||||
id soundArg = [iosOptions objectForKey:@"sound"];
|
||||
id alertArg = [iosOptions objectForKey:@"alert"];
|
||||
id clearBadgeArg = [iosOptions objectForKey:@"clearBadge"];
|
||||
|
||||
if (([badgeArg isKindOfClass:[NSString class]] && [badgeArg isEqualToString:@"true"]) || [badgeArg boolValue])
|
||||
{
|
||||
authorizationOptions |= UNAuthorizationOptionBadge;
|
||||
}
|
||||
|
||||
if (([soundArg isKindOfClass:[NSString class]] && [soundArg isEqualToString:@"true"]) || [soundArg boolValue])
|
||||
{
|
||||
authorizationOptions |= UNAuthorizationOptionSound;
|
||||
}
|
||||
|
||||
if (([alertArg isKindOfClass:[NSString class]] && [alertArg isEqualToString:@"true"]) || [alertArg boolValue])
|
||||
{
|
||||
authorizationOptions |= UNAuthorizationOptionAlert;
|
||||
}
|
||||
|
||||
if (clearBadgeArg == nil || ([clearBadgeArg isKindOfClass:[NSString class]] && [clearBadgeArg isEqualToString:@"false"]) || ![clearBadgeArg boolValue]) {
|
||||
NSLog(@"PushPlugin.register: setting badge to false");
|
||||
clearBadge = NO;
|
||||
} else {
|
||||
NSLog(@"PushPlugin.register: setting badge to true");
|
||||
clearBadge = YES;
|
||||
[[UIApplication sharedApplication] setApplicationIconBadgeNumber:0];
|
||||
}
|
||||
NSLog(@"PushPlugin.register: clear badge is set to %d", clearBadge);
|
||||
|
||||
isInline = NO;
|
||||
|
||||
NSLog(@"PushPlugin.register: better button setup");
|
||||
// setup action buttons
|
||||
NSMutableSet<UNNotificationCategory *> *categories = [[NSMutableSet alloc] init];
|
||||
id categoryOptions = [iosOptions objectForKey:@"categories"];
|
||||
if (categoryOptions != nil && [categoryOptions isKindOfClass:[NSDictionary class]]) {
|
||||
for (id key in categoryOptions) {
|
||||
NSLog(@"categories: key %@", key);
|
||||
id category = [categoryOptions objectForKey:key];
|
||||
|
||||
id yesButton = [category objectForKey:@"yes"];
|
||||
UNNotificationAction *yesAction;
|
||||
if (yesButton != nil && [yesButton isKindOfClass:[NSDictionary class]]) {
|
||||
yesAction = [self createAction: yesButton];
|
||||
}
|
||||
id noButton = [category objectForKey:@"no"];
|
||||
UNNotificationAction *noAction;
|
||||
if (noButton != nil && [noButton isKindOfClass:[NSDictionary class]]) {
|
||||
noAction = [self createAction: noButton];
|
||||
}
|
||||
id maybeButton = [category objectForKey:@"maybe"];
|
||||
UNNotificationAction *maybeAction;
|
||||
if (maybeButton != nil && [maybeButton isKindOfClass:[NSDictionary class]]) {
|
||||
maybeAction = [self createAction: maybeButton];
|
||||
}
|
||||
|
||||
// Identifier to include in your push payload and local notification
|
||||
NSString *identifier = key;
|
||||
|
||||
NSMutableArray<UNNotificationAction *> *actions = [[NSMutableArray alloc] init];
|
||||
if (yesButton != nil) {
|
||||
[actions addObject:yesAction];
|
||||
}
|
||||
if (noButton != nil) {
|
||||
[actions addObject:noAction];
|
||||
}
|
||||
if (maybeButton != nil) {
|
||||
[actions addObject:maybeAction];
|
||||
}
|
||||
|
||||
UNNotificationCategory *notificationCategory = [UNNotificationCategory categoryWithIdentifier:identifier
|
||||
actions:actions
|
||||
intentIdentifiers:@[]
|
||||
options:UNNotificationCategoryOptionNone];
|
||||
|
||||
NSLog(@"Adding category %@", key);
|
||||
[categories addObject:notificationCategory];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
UNUserNotificationCenter *center = [UNUserNotificationCenter currentNotificationCenter];
|
||||
[center setNotificationCategories:categories];
|
||||
[self handleNotificationSettingsWithAuthorizationOptions:[NSNumber numberWithInteger:authorizationOptions]];
|
||||
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self
|
||||
selector:@selector(handleNotificationSettings:)
|
||||
name:pushPluginApplicationDidBecomeActiveNotification
|
||||
object:nil];
|
||||
|
||||
|
||||
|
||||
NSLog(@"Using APNS Notification");
|
||||
[self setUsesFCM:NO];
|
||||
|
||||
id fcmSandboxArg = [iosOptions objectForKey:@"fcmSandbox"];
|
||||
|
||||
if (notificationMessage) { // if there is a pending startup notification
|
||||
dispatch_async(dispatch_get_main_queue(), ^{
|
||||
// delay to allow JS event handlers to be setup
|
||||
[self performSelector:@selector(notificationReceived) withObject:nil afterDelay: 0.5];
|
||||
});
|
||||
}
|
||||
|
||||
}];
|
||||
}
|
||||
}
|
||||
|
||||
- (UNNotificationAction *)createAction:(NSDictionary *)dictionary {
|
||||
NSString *identifier = [dictionary objectForKey:@"callback"];
|
||||
NSString *title = [dictionary objectForKey:@"title"];
|
||||
UNNotificationActionOptions options = UNNotificationActionOptionNone;
|
||||
|
||||
id mode = [dictionary objectForKey:@"foreground"];
|
||||
if (mode != nil && (([mode isKindOfClass:[NSString class]] && [mode isEqualToString:@"true"]) || [mode boolValue])) {
|
||||
options |= UNNotificationActionOptionForeground;
|
||||
}
|
||||
id destructive = [dictionary objectForKey:@"destructive"];
|
||||
if (destructive != nil && (([destructive isKindOfClass:[NSString class]] && [destructive isEqualToString:@"true"]) || [destructive boolValue])) {
|
||||
options |= UNNotificationActionOptionDestructive;
|
||||
}
|
||||
|
||||
return [UNNotificationAction actionWithIdentifier:identifier title:title options:options];
|
||||
}
|
||||
|
||||
- (void)didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken {
|
||||
if (self.callbackId == nil) {
|
||||
NSLog(@"Unexpected call to didRegisterForRemoteNotificationsWithDeviceToken, ignoring: %@", deviceToken);
|
||||
return;
|
||||
}
|
||||
NSLog(@"Push Plugin register success: %@", deviceToken);
|
||||
|
||||
NSString *token = [[[[deviceToken description] stringByReplacingOccurrencesOfString:@"<"withString:@""]
|
||||
stringByReplacingOccurrencesOfString:@">" withString:@""]
|
||||
stringByReplacingOccurrencesOfString: @" " withString: @""];
|
||||
#if !TARGET_IPHONE_SIMULATOR
|
||||
|
||||
// Check what Notifications the user has turned on. We registered for all three, but they may have manually disabled some or all of them.
|
||||
|
||||
UNUserNotificationCenter *center = [UNUserNotificationCenter currentNotificationCenter];
|
||||
__weak PushPlugin *weakSelf = self;
|
||||
[center getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) {
|
||||
|
||||
if(![weakSelf usesFCM]) {
|
||||
[weakSelf registerWithToken: token];
|
||||
}
|
||||
}];
|
||||
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
- (void)didFailToRegisterForRemoteNotificationsWithError:(NSError *)error
|
||||
{
|
||||
if (self.callbackId == nil) {
|
||||
NSLog(@"Unexpected call to didFailToRegisterForRemoteNotificationsWithError, ignoring: %@", error);
|
||||
return;
|
||||
}
|
||||
NSLog(@"Push Plugin register failed");
|
||||
[self failWithMessage:self.callbackId withMsg:@"" withError:error];
|
||||
}
|
||||
|
||||
- (void)notificationReceived {
|
||||
NSLog(@"Notification received");
|
||||
|
||||
if (notificationMessage && self.callbackId != nil)
|
||||
{
|
||||
NSMutableDictionary* message = [NSMutableDictionary dictionaryWithCapacity:4];
|
||||
NSMutableDictionary* additionalData = [NSMutableDictionary dictionaryWithCapacity:4];
|
||||
|
||||
|
||||
for (id key in notificationMessage) {
|
||||
if ([key isEqualToString:@"aps"]) {
|
||||
id aps = [notificationMessage objectForKey:@"aps"];
|
||||
|
||||
for(id key in aps) {
|
||||
NSLog(@"Push Plugin key: %@", key);
|
||||
id value = [aps objectForKey:key];
|
||||
|
||||
if ([key isEqualToString:@"alert"]) {
|
||||
if ([value isKindOfClass:[NSDictionary class]]) {
|
||||
for (id messageKey in value) {
|
||||
id messageValue = [value objectForKey:messageKey];
|
||||
if ([messageKey isEqualToString:@"body"]) {
|
||||
[message setObject:messageValue forKey:@"message"];
|
||||
} else if ([messageKey isEqualToString:@"title"]) {
|
||||
[message setObject:messageValue forKey:@"title"];
|
||||
} else {
|
||||
[additionalData setObject:messageValue forKey:messageKey];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
[message setObject:value forKey:@"message"];
|
||||
}
|
||||
} else if ([key isEqualToString:@"title"]) {
|
||||
[message setObject:value forKey:@"title"];
|
||||
} else if ([key isEqualToString:@"badge"]) {
|
||||
[message setObject:value forKey:@"count"];
|
||||
} else if ([key isEqualToString:@"sound"]) {
|
||||
[message setObject:value forKey:@"sound"];
|
||||
} else if ([key isEqualToString:@"image"]) {
|
||||
[message setObject:value forKey:@"image"];
|
||||
} else {
|
||||
[additionalData setObject:value forKey:key];
|
||||
}
|
||||
}
|
||||
} else {
|
||||
[additionalData setObject:[notificationMessage objectForKey:key] forKey:key];
|
||||
}
|
||||
}
|
||||
|
||||
if (isInline) {
|
||||
[additionalData setObject:[NSNumber numberWithBool:YES] forKey:@"foreground"];
|
||||
} else {
|
||||
[additionalData setObject:[NSNumber numberWithBool:NO] forKey:@"foreground"];
|
||||
}
|
||||
|
||||
if (coldstart) {
|
||||
[additionalData setObject:[NSNumber numberWithBool:YES] forKey:@"coldstart"];
|
||||
} else {
|
||||
[additionalData setObject:[NSNumber numberWithBool:NO] forKey:@"coldstart"];
|
||||
}
|
||||
|
||||
[message setObject:additionalData forKey:@"additionalData"];
|
||||
|
||||
// send notification message
|
||||
CDVPluginResult* pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsDictionary:message];
|
||||
[pluginResult setKeepCallbackAsBool:YES];
|
||||
[self.commandDelegate sendPluginResult:pluginResult callbackId:self.callbackId];
|
||||
|
||||
self.coldstart = NO;
|
||||
self.notificationMessage = nil;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)clearNotification:(CDVInvokedUrlCommand *)command
|
||||
{
|
||||
NSNumber *notId = [command.arguments objectAtIndex:0];
|
||||
[[UNUserNotificationCenter currentNotificationCenter] getDeliveredNotificationsWithCompletionHandler:^(NSArray<UNNotification *> * _Nonnull notifications) {
|
||||
/*
|
||||
* If the server generates a unique "notId" for every push notification, there should only be one match in these arrays, but if not, it will delete
|
||||
* all notifications with the same value for "notId"
|
||||
*/
|
||||
NSPredicate *matchingNotificationPredicate = [NSPredicate predicateWithFormat:@"request.content.userInfo.notId == %@", notId];
|
||||
NSArray<UNNotification *> *matchingNotifications = [notifications filteredArrayUsingPredicate:matchingNotificationPredicate];
|
||||
NSMutableArray<NSString *> *matchingNotificationIdentifiers = [NSMutableArray array];
|
||||
for (UNNotification *notification in matchingNotifications) {
|
||||
[matchingNotificationIdentifiers addObject:notification.request.identifier];
|
||||
}
|
||||
[[UNUserNotificationCenter currentNotificationCenter] removeDeliveredNotificationsWithIdentifiers:matchingNotificationIdentifiers];
|
||||
|
||||
NSString *message = [NSString stringWithFormat:@"Cleared notification with ID: %@", notId];
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:message];
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:command.callbackId];
|
||||
}];
|
||||
}
|
||||
|
||||
- (void)setApplicationIconBadgeNumber:(CDVInvokedUrlCommand *)command
|
||||
{
|
||||
NSMutableDictionary* options = [command.arguments objectAtIndex:0];
|
||||
int badge = [[options objectForKey:@"badge"] intValue] ?: 0;
|
||||
|
||||
[[UIApplication sharedApplication] setApplicationIconBadgeNumber:badge];
|
||||
|
||||
NSString* message = [NSString stringWithFormat:@"app badge count set to %d", badge];
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:message];
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:command.callbackId];
|
||||
}
|
||||
|
||||
- (void)getApplicationIconBadgeNumber:(CDVInvokedUrlCommand *)command
|
||||
{
|
||||
NSInteger badge = [UIApplication sharedApplication].applicationIconBadgeNumber;
|
||||
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsInt:(int)badge];
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:command.callbackId];
|
||||
}
|
||||
|
||||
- (void)clearAllNotifications:(CDVInvokedUrlCommand *)command
|
||||
{
|
||||
[[UIApplication sharedApplication] setApplicationIconBadgeNumber:0];
|
||||
|
||||
NSString* message = [NSString stringWithFormat:@"cleared all notifications"];
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:message];
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:command.callbackId];
|
||||
}
|
||||
|
||||
- (void)hasPermission:(CDVInvokedUrlCommand *)command
|
||||
{
|
||||
id<UIApplicationDelegate> appDelegate = [UIApplication sharedApplication].delegate;
|
||||
if ([appDelegate respondsToSelector:@selector(checkUserHasRemoteNotificationsEnabledWithCompletionHandler:)]) {
|
||||
[appDelegate performSelector:@selector(checkUserHasRemoteNotificationsEnabledWithCompletionHandler:) withObject:^(BOOL isEnabled) {
|
||||
NSMutableDictionary* message = [NSMutableDictionary dictionaryWithCapacity:1];
|
||||
[message setObject:[NSNumber numberWithBool:isEnabled] forKey:@"isEnabled"];
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsDictionary:message];
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:command.callbackId];
|
||||
}];
|
||||
}
|
||||
}
|
||||
|
||||
-(void)successWithMessage:(NSString *)myCallbackId withMsg:(NSString *)message
|
||||
{
|
||||
if (myCallbackId != nil)
|
||||
{
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:message];
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:myCallbackId];
|
||||
}
|
||||
}
|
||||
|
||||
-(void)registerWithToken:(NSString*)token; {
|
||||
// Send result to trigger 'registration' event but keep callback
|
||||
NSMutableDictionary* message = [NSMutableDictionary dictionaryWithCapacity:2];
|
||||
[message setObject:token forKey:@"registrationId"];
|
||||
[message setObject:@"APNS" forKey:@"registrationType"];
|
||||
|
||||
CDVPluginResult* pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsDictionary:message];
|
||||
[pluginResult setKeepCallbackAsBool:YES];
|
||||
[self.commandDelegate sendPluginResult:pluginResult callbackId:self.callbackId];
|
||||
}
|
||||
|
||||
|
||||
-(void)failWithMessage:(NSString *)myCallbackId withMsg:(NSString *)message withError:(NSError *)error
|
||||
{
|
||||
NSString *errorMessage = (error) ? [NSString stringWithFormat:@"%@ - %@", message, [error localizedDescription]] : message;
|
||||
CDVPluginResult *commandResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:errorMessage];
|
||||
|
||||
[self.commandDelegate sendPluginResult:commandResult callbackId:myCallbackId];
|
||||
}
|
||||
|
||||
-(void) finish:(CDVInvokedUrlCommand*)command
|
||||
{
|
||||
NSLog(@"Push Plugin finish called");
|
||||
|
||||
[self.commandDelegate runInBackground:^ {
|
||||
NSString* notId = [command.arguments objectAtIndex:0];
|
||||
|
||||
dispatch_async(dispatch_get_main_queue(), ^{
|
||||
[NSTimer scheduledTimerWithTimeInterval:0.1
|
||||
target:self
|
||||
selector:@selector(stopBackgroundTask:)
|
||||
userInfo:notId
|
||||
repeats:NO];
|
||||
});
|
||||
|
||||
CDVPluginResult* pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK];
|
||||
[self.commandDelegate sendPluginResult:pluginResult callbackId:command.callbackId];
|
||||
}];
|
||||
}
|
||||
|
||||
-(void)stopBackgroundTask:(NSTimer*)timer
|
||||
{
|
||||
UIApplication *app = [UIApplication sharedApplication];
|
||||
|
||||
NSLog(@"Push Plugin stopBackgroundTask called");
|
||||
|
||||
if (handlerObj) {
|
||||
NSLog(@"Push Plugin handlerObj");
|
||||
completionHandler = [handlerObj[[timer userInfo]] copy];
|
||||
if (completionHandler) {
|
||||
NSLog(@"Push Plugin: stopBackgroundTask (remaining t: %f)", app.backgroundTimeRemaining);
|
||||
completionHandler(UIBackgroundFetchResultNewData);
|
||||
completionHandler = nil;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
- (void)pushRegistry:(PKPushRegistry *)registry didUpdatePushCredentials:(PKPushCredentials *)credentials forType:(NSString *)type
|
||||
{
|
||||
if([credentials.token length] == 0) {
|
||||
NSLog(@"VoIPPush Plugin register error - No device token:");
|
||||
return;
|
||||
}
|
||||
|
||||
NSLog(@"VoIPPush Plugin register success");
|
||||
const unsigned *tokenBytes = [credentials.token bytes];
|
||||
NSString *sToken = [NSString stringWithFormat:@"%08x%08x%08x%08x%08x%08x%08x%08x",
|
||||
ntohl(tokenBytes[0]), ntohl(tokenBytes[1]), ntohl(tokenBytes[2]),
|
||||
ntohl(tokenBytes[3]), ntohl(tokenBytes[4]), ntohl(tokenBytes[5]),
|
||||
ntohl(tokenBytes[6]), ntohl(tokenBytes[7])];
|
||||
|
||||
[self registerWithToken:sToken];
|
||||
}
|
||||
|
||||
- (void)pushRegistry:(PKPushRegistry *)registry didReceiveIncomingPushWithPayload:(PKPushPayload *)payload forType:(NSString *)type
|
||||
{
|
||||
NSLog(@"VoIP Notification received");
|
||||
self.notificationMessage = payload.dictionaryPayload;
|
||||
[self notificationReceived];
|
||||
}
|
||||
|
||||
- (void)handleNotificationSettings:(NSNotification *)notification
|
||||
{
|
||||
[self handleNotificationSettingsWithAuthorizationOptions:nil];
|
||||
}
|
||||
|
||||
- (void)handleNotificationSettingsWithAuthorizationOptions:(NSNumber *)authorizationOptionsObject
|
||||
{
|
||||
UNUserNotificationCenter *center = [UNUserNotificationCenter currentNotificationCenter];
|
||||
UNAuthorizationOptions authorizationOptions = [authorizationOptionsObject unsignedIntegerValue];
|
||||
|
||||
__weak UNUserNotificationCenter *weakCenter = center;
|
||||
[center getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) {
|
||||
|
||||
switch (settings.authorizationStatus) {
|
||||
case UNAuthorizationStatusNotDetermined:
|
||||
{
|
||||
[weakCenter requestAuthorizationWithOptions:authorizationOptions completionHandler:^(BOOL granted, NSError * _Nullable error) {
|
||||
if (granted) {
|
||||
[self performSelectorOnMainThread:@selector(registerForRemoteNotifications)
|
||||
withObject:nil
|
||||
waitUntilDone:NO];
|
||||
}
|
||||
}];
|
||||
break;
|
||||
}
|
||||
case UNAuthorizationStatusAuthorized:
|
||||
{
|
||||
[self performSelectorOnMainThread:@selector(registerForRemoteNotifications)
|
||||
withObject:nil
|
||||
waitUntilDone:NO];
|
||||
break;
|
||||
}
|
||||
case UNAuthorizationStatusDenied:
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}];
|
||||
}
|
||||
|
||||
- (void)registerForRemoteNotifications
|
||||
{
|
||||
[[UIApplication sharedApplication] registerForRemoteNotifications];
|
||||
}
|
||||
|
||||
@end
|
||||
25
src/ios/AppDelegate+apnsnotification.h
Normal file
25
src/ios/AppDelegate+apnsnotification.h
Normal file
@@ -0,0 +1,25 @@
|
||||
//
|
||||
// AppDelegate+notification.h
|
||||
// pushtest
|
||||
//
|
||||
// Created by Robert Easterday on 10/26/12.
|
||||
//
|
||||
//
|
||||
|
||||
#import "AppDelegate.h"
|
||||
@import UserNotifications;
|
||||
|
||||
extern NSString *const pushPluginApplicationDidBecomeActiveNotification;
|
||||
|
||||
@interface AppDelegate (notification) <UNUserNotificationCenterDelegate>
|
||||
- (void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken;
|
||||
- (void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *)error;
|
||||
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo fetchCompletionHandler:( void (^)(UIBackgroundFetchResult))completionHandler;
|
||||
- (void)pushPluginOnApplicationDidBecomeActive:(UIApplication *)application;
|
||||
- (void)checkUserHasRemoteNotificationsEnabledWithCompletionHandler:(nonnull void (^)(BOOL))completionHandler;
|
||||
- (id) getCommandInstance:(NSString*)className;
|
||||
|
||||
@property (nonatomic, retain) NSDictionary *launchNotification;
|
||||
@property (nonatomic, retain) NSNumber *coldstart;
|
||||
|
||||
@end
|
||||
289
src/ios/AppDelegate+apnsnotification.m
Normal file
289
src/ios/AppDelegate+apnsnotification.m
Normal file
@@ -0,0 +1,289 @@
|
||||
//
|
||||
// AppDelegate+notification.m
|
||||
// pushtest
|
||||
//
|
||||
// Created by Robert Easterday on 10/26/12.
|
||||
//
|
||||
//
|
||||
|
||||
#import "AppDelegate+apnsnotification.h"
|
||||
#import "APNSPushPlugin.h"
|
||||
#import <objc/runtime.h>
|
||||
|
||||
static char launchNotificationKey;
|
||||
static char coldstartKey;
|
||||
NSString *const pushPluginApplicationDidBecomeActiveNotification = @"pushPluginApplicationDidBecomeActiveNotification";
|
||||
|
||||
|
||||
@implementation AppDelegate (notification)
|
||||
|
||||
- (id) getCommandInstance:(NSString*)className
|
||||
{
|
||||
return [self.viewController getCommandInstance:className];
|
||||
}
|
||||
|
||||
// its dangerous to override a method from within a category.
|
||||
// Instead we will use method swizzling. we set this up in the load call.
|
||||
+ (void)load
|
||||
{
|
||||
static dispatch_once_t onceToken;
|
||||
dispatch_once(&onceToken, ^{
|
||||
Class class = [self class];
|
||||
|
||||
SEL originalSelector = @selector(init);
|
||||
SEL swizzledSelector = @selector(pushPluginSwizzledInit);
|
||||
|
||||
Method original = class_getInstanceMethod(class, originalSelector);
|
||||
Method swizzled = class_getInstanceMethod(class, swizzledSelector);
|
||||
|
||||
BOOL didAddMethod =
|
||||
class_addMethod(class,
|
||||
originalSelector,
|
||||
method_getImplementation(swizzled),
|
||||
method_getTypeEncoding(swizzled));
|
||||
|
||||
if (didAddMethod) {
|
||||
class_replaceMethod(class,
|
||||
swizzledSelector,
|
||||
method_getImplementation(original),
|
||||
method_getTypeEncoding(original));
|
||||
} else {
|
||||
method_exchangeImplementations(original, swizzled);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
- (AppDelegate *)pushPluginSwizzledInit
|
||||
{
|
||||
UNUserNotificationCenter *center = [UNUserNotificationCenter currentNotificationCenter];
|
||||
center.delegate = self;
|
||||
|
||||
[[NSNotificationCenter defaultCenter]addObserver:self
|
||||
selector:@selector(pushPluginOnApplicationDidBecomeActive:)
|
||||
name:UIApplicationDidBecomeActiveNotification
|
||||
object:nil];
|
||||
|
||||
// This actually calls the original init method over in AppDelegate. Equivilent to calling super
|
||||
// on an overrided method, this is not recursive, although it appears that way. neat huh?
|
||||
return [self pushPluginSwizzledInit];
|
||||
}
|
||||
|
||||
- (void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken {
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
[pushHandler didRegisterForRemoteNotificationsWithDeviceToken:deviceToken];
|
||||
}
|
||||
|
||||
- (void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *)error {
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
[pushHandler didFailToRegisterForRemoteNotificationsWithError:error];
|
||||
}
|
||||
|
||||
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo fetchCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler {
|
||||
NSLog(@"didReceiveNotification with fetchCompletionHandler");
|
||||
|
||||
// app is in the background or inactive, so only call notification callback if this is a silent push
|
||||
if (application.applicationState != UIApplicationStateActive) {
|
||||
|
||||
NSLog(@"app in-active");
|
||||
|
||||
// do some convoluted logic to find out if this should be a silent push.
|
||||
long silent = 0;
|
||||
id aps = [userInfo objectForKey:@"aps"];
|
||||
id contentAvailable = [aps objectForKey:@"content-available"];
|
||||
if ([contentAvailable isKindOfClass:[NSString class]] && [contentAvailable isEqualToString:@"1"]) {
|
||||
silent = 1;
|
||||
} else if ([contentAvailable isKindOfClass:[NSNumber class]]) {
|
||||
silent = [contentAvailable integerValue];
|
||||
}
|
||||
|
||||
if (silent == 1) {
|
||||
NSLog(@"this should be a silent push");
|
||||
void (^safeHandler)(UIBackgroundFetchResult) = ^(UIBackgroundFetchResult result){
|
||||
dispatch_async(dispatch_get_main_queue(), ^{
|
||||
completionHandler(result);
|
||||
});
|
||||
};
|
||||
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
|
||||
if (pushHandler.handlerObj == nil) {
|
||||
pushHandler.handlerObj = [NSMutableDictionary dictionaryWithCapacity:2];
|
||||
}
|
||||
|
||||
id notId = [userInfo objectForKey:@"notId"];
|
||||
if (notId != nil) {
|
||||
NSLog(@"Push Plugin notId %@", notId);
|
||||
[pushHandler.handlerObj setObject:safeHandler forKey:notId];
|
||||
} else {
|
||||
NSLog(@"Push Plugin notId handler");
|
||||
[pushHandler.handlerObj setObject:safeHandler forKey:@"handler"];
|
||||
}
|
||||
|
||||
pushHandler.notificationMessage = userInfo;
|
||||
pushHandler.isInline = NO;
|
||||
[pushHandler notificationReceived];
|
||||
} else {
|
||||
NSLog(@"just put it in the shade");
|
||||
//save it for later
|
||||
self.launchNotification = userInfo;
|
||||
completionHandler(UIBackgroundFetchResultNewData);
|
||||
}
|
||||
|
||||
} else {
|
||||
completionHandler(UIBackgroundFetchResultNoData);
|
||||
}
|
||||
}
|
||||
|
||||
- (void)checkUserHasRemoteNotificationsEnabledWithCompletionHandler:(nonnull void (^)(BOOL))completionHandler
|
||||
{
|
||||
[[UNUserNotificationCenter currentNotificationCenter] getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) {
|
||||
|
||||
switch (settings.authorizationStatus)
|
||||
{
|
||||
case UNAuthorizationStatusDenied:
|
||||
case UNAuthorizationStatusNotDetermined:
|
||||
completionHandler(NO);
|
||||
break;
|
||||
case UNAuthorizationStatusAuthorized:
|
||||
completionHandler(YES);
|
||||
break;
|
||||
}
|
||||
}];
|
||||
}
|
||||
|
||||
- (void)pushPluginOnApplicationDidBecomeActive:(NSNotification *)notification {
|
||||
|
||||
NSLog(@"active");
|
||||
|
||||
NSString *firstLaunchKey = @"firstLaunchKey";
|
||||
NSUserDefaults *defaults = [[NSUserDefaults alloc] initWithSuiteName:@"phonegap-plugin-push"];
|
||||
if (![defaults boolForKey:firstLaunchKey]) {
|
||||
NSLog(@"application first launch: remove badge icon number");
|
||||
[defaults setBool:YES forKey:firstLaunchKey];
|
||||
[[UIApplication sharedApplication] setApplicationIconBadgeNumber:0];
|
||||
}
|
||||
|
||||
UIApplication *application = notification.object;
|
||||
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
if (pushHandler.clearBadge) {
|
||||
NSLog(@"PushPlugin clearing badge");
|
||||
//zero badge
|
||||
application.applicationIconBadgeNumber = 0;
|
||||
} else {
|
||||
NSLog(@"PushPlugin skip clear badge");
|
||||
}
|
||||
|
||||
if (self.launchNotification) {
|
||||
pushHandler.isInline = NO;
|
||||
pushHandler.coldstart = [self.coldstart boolValue];
|
||||
pushHandler.notificationMessage = self.launchNotification;
|
||||
self.launchNotification = nil;
|
||||
self.coldstart = [NSNumber numberWithBool:NO];
|
||||
[pushHandler performSelectorOnMainThread:@selector(notificationReceived) withObject:pushHandler waitUntilDone:NO];
|
||||
}
|
||||
|
||||
[[NSNotificationCenter defaultCenter] postNotificationName:pushPluginApplicationDidBecomeActiveNotification object:nil];
|
||||
}
|
||||
|
||||
- (void)userNotificationCenter:(UNUserNotificationCenter *)center
|
||||
willPresentNotification:(UNNotification *)notification
|
||||
withCompletionHandler:(void (^)(UNNotificationPresentationOptions options))completionHandler
|
||||
{
|
||||
NSLog( @"NotificationCenter Handle push from foreground" );
|
||||
// custom code to handle push while app is in the foreground
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
pushHandler.notificationMessage = notification.request.content.userInfo;
|
||||
pushHandler.isInline = YES;
|
||||
[pushHandler notificationReceived];
|
||||
|
||||
completionHandler(UNNotificationPresentationOptionNone);
|
||||
}
|
||||
|
||||
- (void)userNotificationCenter:(UNUserNotificationCenter *)center
|
||||
didReceiveNotificationResponse:(UNNotificationResponse *)response
|
||||
withCompletionHandler:(void(^)(void))completionHandler
|
||||
{
|
||||
NSLog(@"Push Plugin didReceiveNotificationResponse: actionIdentifier %@, notification: %@", response.actionIdentifier,
|
||||
response.notification.request.content.userInfo);
|
||||
NSMutableDictionary *userInfo = [response.notification.request.content.userInfo mutableCopy];
|
||||
[userInfo setObject:response.actionIdentifier forKey:@"actionCallback"];
|
||||
NSLog(@"Push Plugin userInfo %@", userInfo);
|
||||
|
||||
switch ([UIApplication sharedApplication].applicationState) {
|
||||
case UIApplicationStateActive:
|
||||
{
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
pushHandler.notificationMessage = userInfo;
|
||||
pushHandler.isInline = NO;
|
||||
[pushHandler notificationReceived];
|
||||
completionHandler();
|
||||
break;
|
||||
}
|
||||
case UIApplicationStateInactive:
|
||||
{
|
||||
NSLog(@"coldstart");
|
||||
self.launchNotification = response.notification.request.content.userInfo;
|
||||
self.coldstart = [NSNumber numberWithBool:YES];
|
||||
break;
|
||||
}
|
||||
case UIApplicationStateBackground:
|
||||
{
|
||||
void (^safeHandler)(void) = ^(void){
|
||||
dispatch_async(dispatch_get_main_queue(), ^{
|
||||
completionHandler();
|
||||
});
|
||||
};
|
||||
|
||||
PushPlugin *pushHandler = [self getCommandInstance:@"APNSPushNotification"];
|
||||
|
||||
if (pushHandler.handlerObj == nil) {
|
||||
pushHandler.handlerObj = [NSMutableDictionary dictionaryWithCapacity:2];
|
||||
}
|
||||
|
||||
id notId = [userInfo objectForKey:@"notId"];
|
||||
if (notId != nil) {
|
||||
NSLog(@"Push Plugin notId %@", notId);
|
||||
[pushHandler.handlerObj setObject:safeHandler forKey:notId];
|
||||
} else {
|
||||
NSLog(@"Push Plugin notId handler");
|
||||
[pushHandler.handlerObj setObject:safeHandler forKey:@"handler"];
|
||||
}
|
||||
|
||||
pushHandler.notificationMessage = userInfo;
|
||||
pushHandler.isInline = NO;
|
||||
|
||||
[pushHandler performSelectorOnMainThread:@selector(notificationReceived) withObject:pushHandler waitUntilDone:NO];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// The accessors use an Associative Reference since you can't define a iVar in a category
|
||||
// http://developer.apple.com/library/ios/#documentation/cocoa/conceptual/objectivec/Chapters/ocAssociativeReferences.html
|
||||
- (NSMutableArray *)launchNotification
|
||||
{
|
||||
return objc_getAssociatedObject(self, &launchNotificationKey);
|
||||
}
|
||||
|
||||
- (void)setLaunchNotification:(NSDictionary *)aDictionary
|
||||
{
|
||||
objc_setAssociatedObject(self, &launchNotificationKey, aDictionary, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
|
||||
}
|
||||
|
||||
- (NSNumber *)coldstart
|
||||
{
|
||||
return objc_getAssociatedObject(self, &coldstartKey);
|
||||
}
|
||||
|
||||
- (void)setColdstart:(NSNumber *)aNumber
|
||||
{
|
||||
objc_setAssociatedObject(self, &coldstartKey, aNumber, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
|
||||
}
|
||||
|
||||
- (void)dealloc
|
||||
{
|
||||
self.launchNotification = nil; // clear the association and release the object
|
||||
self.coldstart = nil;
|
||||
}
|
||||
|
||||
@end
|
||||
393
www/apnspush.js
Normal file
393
www/apnspush.js
Normal file
@@ -0,0 +1,393 @@
|
||||
/**
|
||||
* This file has been generated by Babel.
|
||||
*
|
||||
* DO NOT EDIT IT DIRECTLY
|
||||
*
|
||||
* Edit the JS source file src/js/push.js
|
||||
**/'use strict';
|
||||
|
||||
var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
|
||||
|
||||
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
|
||||
|
||||
/* global cordova:false */
|
||||
/* globals window */
|
||||
|
||||
/*!
|
||||
* Module dependencies.
|
||||
*/
|
||||
|
||||
var exec = cordova.require('cordova/exec');
|
||||
|
||||
var APNSPushNotification = function () {
|
||||
/**
|
||||
* APNSPushNotification constructor.
|
||||
*
|
||||
* @param {Object} options to initiate Push Notifications.
|
||||
* @return {APNSPushNotification} instance that can be monitored and cancelled.
|
||||
*/
|
||||
function APNSPushNotification(options) {
|
||||
var _this = this;
|
||||
|
||||
_classCallCheck(this, APNSPushNotification);
|
||||
|
||||
this.handlers = {
|
||||
registration: [],
|
||||
notification: [],
|
||||
error: []
|
||||
};
|
||||
|
||||
// require options parameter
|
||||
if (typeof options === 'undefined') {
|
||||
throw new Error('The options argument is required.');
|
||||
}
|
||||
|
||||
// store the options to this object instance
|
||||
this.options = options;
|
||||
|
||||
// triggered on registration and notification
|
||||
var success = function success(result) {
|
||||
if (result && typeof result.registrationId !== 'undefined') {
|
||||
_this.emit('registration', result);
|
||||
} else if (result && result.additionalData && typeof result.additionalData.actionCallback !== 'undefined') {
|
||||
_this.emit(result.additionalData.actionCallback, result);
|
||||
} else if (result) {
|
||||
_this.emit('notification', result);
|
||||
}
|
||||
};
|
||||
|
||||
// triggered on error
|
||||
var fail = function fail(msg) {
|
||||
var e = typeof msg === 'string' ? new Error(msg) : msg;
|
||||
_this.emit('error', e);
|
||||
};
|
||||
|
||||
// wait at least one process tick to allow event subscriptions
|
||||
setTimeout(function () {
|
||||
exec(success, fail, 'APNSPushNotification', 'init', [options]);
|
||||
}, 10);
|
||||
}
|
||||
|
||||
/**
|
||||
* Unregister from push notifications
|
||||
*/
|
||||
|
||||
|
||||
_createClass(APNSPushNotification, [{
|
||||
key: 'unregister',
|
||||
value: function unregister(successCallback) {
|
||||
var _this2 = this;
|
||||
|
||||
var errorCallback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : function () {};
|
||||
var options = arguments[2];
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('APNSPushNotification.unregister failure: failure parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('APNSPushNotification.unregister failure: success callback parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
var cleanHandlersAndPassThrough = function cleanHandlersAndPassThrough() {
|
||||
if (!options) {
|
||||
_this2.handlers = {
|
||||
registration: [],
|
||||
notification: [],
|
||||
error: []
|
||||
};
|
||||
}
|
||||
successCallback();
|
||||
};
|
||||
|
||||
exec(cleanHandlersAndPassThrough, errorCallback, 'APNSPushNotification', 'unregister', [options]);
|
||||
}
|
||||
|
||||
/**
|
||||
* subscribe to a topic
|
||||
* @param {String} topic topic to subscribe
|
||||
* @param {Function} successCallback success callback
|
||||
* @param {Function} errorCallback error callback
|
||||
* @return {void}
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'subscribe',
|
||||
value: function subscribe(topic, successCallback) {
|
||||
var errorCallback = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : function () {};
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('APNSPushNotification.subscribe failure: failure parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('APNSPushNotification.subscribe failure: success callback parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'subscribe', [topic]);
|
||||
}
|
||||
|
||||
/**
|
||||
* unsubscribe to a topic
|
||||
* @param {String} topic topic to unsubscribe
|
||||
* @param {Function} successCallback success callback
|
||||
* @param {Function} errorCallback error callback
|
||||
* @return {void}
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'unsubscribe',
|
||||
value: function unsubscribe(topic, successCallback) {
|
||||
var errorCallback = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : function () {};
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('APNSPushNotification.unsubscribe failure: failure parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('APNSPushNotification.unsubscribe failure: success callback parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'unsubscribe', [topic]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Call this to set the application icon badge
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'setApplicationIconBadgeNumber',
|
||||
value: function setApplicationIconBadgeNumber(successCallback) {
|
||||
var errorCallback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : function () {};
|
||||
var badge = arguments[2];
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('APNSPushNotification.setApplicationIconBadgeNumber failure: failure ' + 'parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('APNSPushNotification.setApplicationIconBadgeNumber failure: success ' + 'callback parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'setApplicationIconBadgeNumber', [{ badge: badge }]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the application icon badge
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'getApplicationIconBadgeNumber',
|
||||
value: function getApplicationIconBadgeNumber(successCallback) {
|
||||
var errorCallback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : function () {};
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('APNSPushNotification.getApplicationIconBadgeNumber failure: failure ' + 'parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('APNSPushNotification.getApplicationIconBadgeNumber failure: success ' + 'callback parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'getApplicationIconBadgeNumber', []);
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear all notifications
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'clearAllNotifications',
|
||||
value: function clearAllNotifications() {
|
||||
var successCallback = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : function () {};
|
||||
var errorCallback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : function () {};
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('APNSPushNotification.clearAllNotifications failure: failure parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('APNSPushNotification.clearAllNotifications failure: success callback ' + 'parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'clearAllNotifications', []);
|
||||
}
|
||||
|
||||
/**
|
||||
* Clears notifications that have the ID specified.
|
||||
* @param {Function} [successCallback] Callback function to be called on success.
|
||||
* @param {Function} [errorCallback] Callback function to be called when an error is encountered.
|
||||
* @param {Number} id ID of the notification to be removed.
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'clearNotification',
|
||||
value: function clearNotification() {
|
||||
var successCallback = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : function () {};
|
||||
var errorCallback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : function () {};
|
||||
var id = arguments[2];
|
||||
|
||||
var idNumber = parseInt(id, 10);
|
||||
if (isNaN(idNumber) || idNumber > Number.MAX_SAFE_INTEGER || idNumber < 0) {
|
||||
console.log('APNSPushNotification.clearNotification failure: id parameter must' + 'be a valid integer.');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'clearNotification', [idNumber]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Listen for an event.
|
||||
*
|
||||
* The following events are supported:
|
||||
*
|
||||
* - registration
|
||||
* - notification
|
||||
* - error
|
||||
*
|
||||
* @param {String} eventName to subscribe to.
|
||||
* @param {Function} callback triggered on the event.
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'on',
|
||||
value: function on(eventName, callback) {
|
||||
if (!this.handlers.hasOwnProperty(eventName)) {
|
||||
this.handlers[eventName] = [];
|
||||
}
|
||||
this.handlers[eventName].push(callback);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove event listener.
|
||||
*
|
||||
* @param {String} eventName to match subscription.
|
||||
* @param {Function} handle function associated with event.
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'off',
|
||||
value: function off(eventName, handle) {
|
||||
if (this.handlers.hasOwnProperty(eventName)) {
|
||||
var handleIndex = this.handlers[eventName].indexOf(handle);
|
||||
if (handleIndex >= 0) {
|
||||
this.handlers[eventName].splice(handleIndex, 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Emit an event.
|
||||
*
|
||||
* This is intended for internal use only.
|
||||
*
|
||||
* @param {String} eventName is the event to trigger.
|
||||
* @param {*} all arguments are passed to the event listeners.
|
||||
*
|
||||
* @return {Boolean} is true when the event is triggered otherwise false.
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: 'emit',
|
||||
value: function emit() {
|
||||
for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {
|
||||
args[_key] = arguments[_key];
|
||||
}
|
||||
|
||||
var eventName = args.shift();
|
||||
|
||||
if (!this.handlers.hasOwnProperty(eventName)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (var i = 0, length = this.handlers[eventName].length; i < length; i++) {
|
||||
var callback = this.handlers[eventName][i];
|
||||
if (typeof callback === 'function') {
|
||||
callback.apply(undefined, args);
|
||||
} else {
|
||||
console.log('event handler: ' + eventName + ' must be a function');
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}, {
|
||||
key: 'finish',
|
||||
value: function finish() {
|
||||
var successCallback = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : function () {};
|
||||
var errorCallback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : function () {};
|
||||
var id = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'handler';
|
||||
|
||||
if (typeof successCallback !== 'function') {
|
||||
console.log('finish failure: success callback parameter must be a function');
|
||||
return;
|
||||
}
|
||||
|
||||
if (typeof errorCallback !== 'function') {
|
||||
console.log('finish failure: failure parameter not a function');
|
||||
return;
|
||||
}
|
||||
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'finish', [id]);
|
||||
}
|
||||
}]);
|
||||
|
||||
return APNSPushNotification;
|
||||
}();
|
||||
|
||||
/*!
|
||||
* Push Notification Plugin.
|
||||
*/
|
||||
|
||||
module.exports = {
|
||||
/**
|
||||
* Register for Push Notifications.
|
||||
*
|
||||
* This method will instantiate a new copy of the APNSPushNotification object
|
||||
* and start the registration process.
|
||||
*
|
||||
* @param {Object} options
|
||||
* @return {APNSPushNotification} instance
|
||||
*/
|
||||
|
||||
init: function init(options) {
|
||||
return new APNSPushNotification(options);
|
||||
},
|
||||
|
||||
hasPermission: function hasPermission(successCallback, errorCallback) {
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'hasPermission', []);
|
||||
},
|
||||
|
||||
createChannel: function createChannel(successCallback, errorCallback, channel) {
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'createChannel', [channel]);
|
||||
},
|
||||
|
||||
deleteChannel: function deleteChannel(successCallback, errorCallback, channelId) {
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'deleteChannel', [channelId]);
|
||||
},
|
||||
|
||||
listChannels: function listChannels(successCallback, errorCallback) {
|
||||
exec(successCallback, errorCallback, 'APNSPushNotification', 'listChannels', []);
|
||||
},
|
||||
|
||||
/**
|
||||
* APNSPushNotification Object.
|
||||
*
|
||||
* Expose the APNSPushNotification object for direct use
|
||||
* and testing. Typically, you should use the
|
||||
* .init helper method.
|
||||
*/
|
||||
APNSPushNotification: APNSPushNotification
|
||||
};
|
||||
Reference in New Issue
Block a user