@adobe/react-native-aepmessaging 1.0.0-beta.2 → 1.0.0-beta.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/RCTAEPMessaging.podspec +1 -1
- package/README.md +280 -16
- package/android/build.gradle +4 -1
- package/android/libs/messaging.aar +0 -0
- package/android/libs/optimize.aar +0 -0
- package/android/src/main/java/com/adobe/marketing/mobile/reactnative/messaging/RCTAEPMessagingModule.java +238 -14
- package/ios/src/RCTAEPMessaging.h +6 -3
- package/ios/src/RCTAEPMessaging.m +171 -3
- package/js/Messaging.d.ts +29 -2
- package/js/Messaging.js +56 -2
- package/js/Messaging.js.map +1 -1
- package/js/index.d.ts +4 -1
- package/js/index.js +6 -2
- package/js/index.js.map +1 -1
- package/js/models/Message.d.ts +43 -0
- package/js/models/Message.js +80 -0
- package/js/models/Message.js.map +1 -0
- package/js/models/MessagingDelegate.d.ts +25 -0
- package/js/models/MessagingDelegate.js +14 -0
- package/js/models/MessagingDelegate.js.map +1 -0
- package/js/models/MessagingEdgeEventType.d.ts +9 -0
- package/js/models/MessagingEdgeEventType.js +25 -0
- package/js/models/MessagingEdgeEventType.js.map +1 -0
- package/package.json +5 -5
- package/ts/Messaging.ts +75 -7
- package/ts/index.ts +4 -1
- package/ts/models/Message.ts +82 -0
- package/ts/models/MessagingDelegate.ts +41 -0
- package/ts/models/MessagingEdgeEventType.ts +22 -0
- package/tsconfig.json +2 -1
package/RCTAEPMessaging.podspec
CHANGED
package/README.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
|
|
2
2
|
# React Native Adobe Experience Platform Messaging Extension
|
|
3
3
|
|
|
4
|
-
[](https://www.npmjs.com/package/@adobe/react-native-aepmessaging)
|
|
4
|
+
[](https://www.npmjs.com/package/@adobe/react-native-aepmessaging)
|
|
5
5
|
[](https://www.npmjs.com/package/@adobe/react-native-aepmessaging)
|
|
6
6
|
|
|
7
7
|
`@adobe/react-native-aepmessaging` is a wrapper around the iOS and Android [Adobe Journey Optimizer Messaging](https://aep-sdks.gitbook.io/docs/using-mobile-extensions/adobe-journey-optimizer) to allow for integration with React Native applications.
|
|
@@ -15,18 +15,46 @@ The messaging extension has the following peer dependenices, which must be insta
|
|
|
15
15
|
|
|
16
16
|
## Installation
|
|
17
17
|
|
|
18
|
-
See [Requirements and Installation](https://github.com/adobe/aepsdk-react-native#requirements) instructions on the main page
|
|
18
|
+
See [Requirements and Installation](https://github.com/adobe/aepsdk-react-native#requirements) instructions on the main page
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
**Installation instructions for `@adobe/react-native-aepmessaging` v1.0.0-beta.2 with in-app messaging support**
|
|
21
|
+
Clone the `@adobe/react-native-aepmessaging` package from the `messaging` branch on [Github](https://github.com/adobe/aepsdk-react-native/tree/messaging). Place the Messaging package folder into app repo or directory of your choosing. Then you can install the package by running:
|
|
21
22
|
|
|
22
23
|
```bash
|
|
23
24
|
cd MyReactApp
|
|
24
|
-
npm install
|
|
25
|
+
npm install {path to messaging package}
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
## IOS Setup
|
|
29
|
+
|
|
30
|
+
**Podfile setup for `@adobe/react-native-aepmessaging` v1.0.0-beta.2 with in-app messaging support**
|
|
31
|
+
The In app Message APIs depends on the AEP Messaging iOS SDK v1.1.0-beta. This version is not yet published to the Cocoapods but is available in the public [github repository](https://github.com/adobe/aepsdk-messaging-ios/tree/staging). Add the following pod dependency in your applications Podfile under the application target.
|
|
32
|
+
|
|
33
|
+
```ruby
|
|
34
|
+
target 'AEPSampleApp' do
|
|
35
|
+
pod "AEPMessaging", :git => "https://github.com/adobe/aepsdk-messaging-ios.git", :branch => "staging"
|
|
36
|
+
end
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
## Android Setup
|
|
40
|
+
|
|
41
|
+
**Gradle setup for `@adobe/react-native-aepmessaging` v1.0.0-beta.2 with in-app messaging support**
|
|
42
|
+
AEPMessaging Android SDK v1.2.0-beta.2 with in-app messaging support is published to maven snapshots. In project level build.gradle file of Android project in your RN application add `maven { url "https://oss.sonatype.org/content/repositories/snapshots/" }` in `allprojects -> repositories`.
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
```gradle
|
|
46
|
+
repositories {
|
|
47
|
+
google()
|
|
48
|
+
mavenCentral()
|
|
49
|
+
maven {
|
|
50
|
+
url "https://oss.sonatype.org/content/repositories/snapshots/"
|
|
51
|
+
}
|
|
52
|
+
}
|
|
25
53
|
```
|
|
26
54
|
|
|
27
55
|
## Usage
|
|
28
56
|
|
|
29
|
-
### [Messaging](https://aep-sdks.gitbook.io/docs/
|
|
57
|
+
### [Messaging](https://aep-sdks.gitbook.io/docs/beta/iam)
|
|
30
58
|
|
|
31
59
|
### Installing and registering the extension with the AEP Mobile Core
|
|
32
60
|
|
|
@@ -42,16 +70,16 @@ iOS
|
|
|
42
70
|
@import AEPEdge;
|
|
43
71
|
@import AEPEdgeIdentity;
|
|
44
72
|
@import AEPMessaging;
|
|
73
|
+
@import AEPOptimize;
|
|
45
74
|
...
|
|
46
75
|
@implementation AppDelegate
|
|
47
76
|
-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
|
|
48
|
-
[AEPMobileCore setLogLevel:
|
|
49
|
-
[AEPMobileCore
|
|
50
|
-
|
|
77
|
+
[AEPMobileCore setLogLevel: AEPLogLevelTrace];
|
|
78
|
+
[AEPMobileCore registerExtensions: @[AEPMobileEdgeIdentity.class, AEPMobileEdge.class, AEPMobileMessaging.class, AEPMobileOptimize.class] completion:^{
|
|
79
|
+
[AEPMobileCore configureWithAppId:@"yourAppID"];
|
|
51
80
|
[AEPMobileCore lifecycleStart:@{@"contextDataKey": @"contextDataVal"}];
|
|
52
81
|
}
|
|
53
82
|
];
|
|
54
|
-
|
|
55
83
|
return YES;
|
|
56
84
|
}
|
|
57
85
|
|
|
@@ -66,9 +94,10 @@ import com.adobe.marketing.mobile.Lifecycle;
|
|
|
66
94
|
import com.adobe.marketing.mobile.LoggingMode;
|
|
67
95
|
import com.adobe.marketing.mobile.MobileCore;
|
|
68
96
|
import com.adobe.marketing.mobile.Edge;
|
|
69
|
-
import com.adobe.marketing.mobile.edge.identity;
|
|
97
|
+
import com.adobe.marketing.mobile.edge.identity.Identity;
|
|
70
98
|
import com.adobe.marketing.mobile.Messaging;
|
|
71
|
-
|
|
99
|
+
import com.adobe.marketing.mobile.optimize.Optimize;
|
|
100
|
+
|
|
72
101
|
...
|
|
73
102
|
import android.app.Application;
|
|
74
103
|
...
|
|
@@ -83,6 +112,7 @@ public class MainApplication extends Application implements ReactApplication {
|
|
|
83
112
|
try {
|
|
84
113
|
Edge.registerExtension();
|
|
85
114
|
Identity.registerExtension();
|
|
115
|
+
Optimize.registerExtension();
|
|
86
116
|
Messaging.registerExtension();
|
|
87
117
|
MobileCore.configureWithAppID("yourAppID");
|
|
88
118
|
MobileCore.start(new AdobeCallback() {
|
|
@@ -101,11 +131,12 @@ public class MainApplication extends Application implements ReactApplication {
|
|
|
101
131
|
### Importing the extension:
|
|
102
132
|
|
|
103
133
|
```javascript
|
|
104
|
-
import {
|
|
134
|
+
import { Messaging, MessagingDelegate, MessagingEdgeEventType, Message } from '@adobe/react-native-aepmessaging';
|
|
105
135
|
```
|
|
106
136
|
|
|
107
137
|
## API reference
|
|
108
138
|
### extensionVersion
|
|
139
|
+
Returns the version of the AEPMessaging extension
|
|
109
140
|
|
|
110
141
|
**Syntax**
|
|
111
142
|
```javascript
|
|
@@ -117,18 +148,251 @@ extensionVersion(): Promise<string>;
|
|
|
117
148
|
Messaging.extensionVersion().then(version => console.log("AdobeExperienceSDK: Messaging version: " + version));
|
|
118
149
|
```
|
|
119
150
|
|
|
120
|
-
## Configure Adobe Journey Optimizer
|
|
151
|
+
## Configure Adobe Journey Optimizer
|
|
121
152
|
To configure Adobe Journey optimizer Messaging in Launch follow steps in [Configure Adobe Journey optimizer](https://aep-sdks.gitbook.io/docs/using-mobile-extensions/adobe-journey-optimizer#setup-adobe-journey-optimizer-extension)
|
|
122
153
|
|
|
123
154
|
## Push Notification Setup
|
|
124
|
-
Handling push notifications must be done in native (Android/iOS) code for the React Native app. To configure push notification in the native project, follow the instructions provided by their respective platforms:
|
|
155
|
+
Handling push notifications must be done in native (Android/iOS) code for the React Native app. To configure push notification in the native project, follow the instructions provided by their respective platforms:
|
|
125
156
|
- [Apple - iOS push notification setup](https://developer.apple.com/documentation/usernotifications/registering_your_app_with_apns)
|
|
126
157
|
- [Google - Android push notification setup](https://firebase.google.com/docs/cloud-messaging/android/client)
|
|
127
158
|
|
|
128
|
-
## Messaging
|
|
129
|
-
|
|
159
|
+
## Push Messaging APIs usage
|
|
160
|
+
Push messaging APIs in the SDK must be called from the native Android/iOS project of React Native app.
|
|
130
161
|
|
|
131
162
|
###### [iOS API usage](https://github.com/adobe/aepsdk-messaging-ios/blob/main/Documentation/APIUsage.md)
|
|
132
163
|
|
|
133
164
|
##### [Android API usage](https://github.com/adobe/aepsdk-messaging-android/blob/main/Documentation/APIUsage.md)
|
|
134
165
|
In Android, [MessagingPushPayload](https://github.com/adobe/aepsdk-messaging-android/blob/main/Documentation/push/MessagingPushPayload.md#messagingpushpayload-usage) can be used for getting the notification attributes like title, body, and action. These are useful for push notification creation.
|
|
166
|
+
|
|
167
|
+
## In-app messages API reference
|
|
168
|
+
### refreshInAppMessages
|
|
169
|
+
Initiates a network call to retrieve remote in-app message definitions.
|
|
170
|
+
|
|
171
|
+
**Syntax**
|
|
172
|
+
```javascript
|
|
173
|
+
refreshInAppMessages()
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
**Example**
|
|
177
|
+
```javascript
|
|
178
|
+
Messaging.refreshInAppMessages();
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
### setMessagingDelegate
|
|
182
|
+
Sets the MessagingDelegate in AEPCore to listen the Message lifecycle events.
|
|
183
|
+
|
|
184
|
+
**Syntax**
|
|
185
|
+
```javascript
|
|
186
|
+
setMessagingDelegate(delegate: MessagingDelegate);
|
|
187
|
+
```
|
|
188
|
+
|
|
189
|
+
**Example**
|
|
190
|
+
```javascript
|
|
191
|
+
const messagingDelegate = {
|
|
192
|
+
|
|
193
|
+
onShow(message: Message) {
|
|
194
|
+
// Action after message is displayed.
|
|
195
|
+
},
|
|
196
|
+
|
|
197
|
+
onDismiss(message: Message) {
|
|
198
|
+
// Action after message is dismissed.
|
|
199
|
+
},
|
|
200
|
+
|
|
201
|
+
shouldShowMessage(message: Message) {
|
|
202
|
+
return true; //Return true to show the Message else return false
|
|
203
|
+
},
|
|
204
|
+
|
|
205
|
+
urlLoaded(url: string, message: Message) {
|
|
206
|
+
// Action after message loads an URL
|
|
207
|
+
}
|
|
208
|
+
};
|
|
209
|
+
|
|
210
|
+
Messaging.setMessagingDelegate(messagingDelegate);
|
|
211
|
+
```
|
|
212
|
+
|
|
213
|
+
### saveMessage
|
|
214
|
+
Natively caches the provided Message object in-memory. Cached Message object can be later use to show message or perform other actions on the Message object. This function should be called from **shouldShowMessage** of MessagingDelegate.
|
|
215
|
+
|
|
216
|
+
**Syntax**
|
|
217
|
+
```javascript
|
|
218
|
+
saveMessage(message: Message);
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
**Example**
|
|
222
|
+
```javascript
|
|
223
|
+
Messaging.saveMessage(message);
|
|
224
|
+
```
|
|
225
|
+
|
|
226
|
+
## Handling In App Messages using Message Object
|
|
227
|
+
The Message Object passed to the Messaging delegate contains the following functions to handle a message
|
|
228
|
+
|
|
229
|
+
### show
|
|
230
|
+
Signals to the UIServices that the message should be shown.
|
|
231
|
+
|
|
232
|
+
**Syntax**
|
|
233
|
+
```javascript
|
|
234
|
+
show();
|
|
235
|
+
```
|
|
236
|
+
|
|
237
|
+
**Example**
|
|
238
|
+
```javascript
|
|
239
|
+
var message: Message;
|
|
240
|
+
message.show();
|
|
241
|
+
```
|
|
242
|
+
|
|
243
|
+
### dismiss
|
|
244
|
+
Signals to the UIServices that the message should be dismissed.
|
|
245
|
+
|
|
246
|
+
**Syntax**
|
|
247
|
+
```javascript
|
|
248
|
+
dismiss(suppressAutoTrack: ?boolean = false);
|
|
249
|
+
```
|
|
250
|
+
|
|
251
|
+
**Example**
|
|
252
|
+
```javascript
|
|
253
|
+
var message: Message;
|
|
254
|
+
message.dismiss(true);
|
|
255
|
+
```
|
|
256
|
+
|
|
257
|
+
### track
|
|
258
|
+
Generates an Edge Event for the provided interaction and eventType.
|
|
259
|
+
|
|
260
|
+
**Syntax**
|
|
261
|
+
```javascript
|
|
262
|
+
track(interaction: ?string, eventType: MessagingEdgeEventType);
|
|
263
|
+
```
|
|
264
|
+
|
|
265
|
+
**Example**
|
|
266
|
+
```javascript
|
|
267
|
+
var message: Message;
|
|
268
|
+
message.track("sample text", MessagingEdgeEventType.IN_APP_DISMISS);
|
|
269
|
+
```
|
|
270
|
+
|
|
271
|
+
### handleJavascriptMessage
|
|
272
|
+
Adds a handler for Javascript messages sent from the message's webview.
|
|
273
|
+
|
|
274
|
+
**Syntax**
|
|
275
|
+
```javascript
|
|
276
|
+
handleJavascriptMessage(name: string) : Promise<?any>;
|
|
277
|
+
```
|
|
278
|
+
|
|
279
|
+
**Example**
|
|
280
|
+
```javascript
|
|
281
|
+
var message: Message;
|
|
282
|
+
message.handleJavascriptMessage("test").then((data) => {
|
|
283
|
+
|
|
284
|
+
});
|
|
285
|
+
```
|
|
286
|
+
|
|
287
|
+
### setAutoTrack
|
|
288
|
+
Enables/Disables the autotracking for the Message events.
|
|
289
|
+
|
|
290
|
+
**Syntax**
|
|
291
|
+
```javascript
|
|
292
|
+
setAutoTrack(autoTrack: boolean);
|
|
293
|
+
```
|
|
294
|
+
|
|
295
|
+
**Example**
|
|
296
|
+
```javascript
|
|
297
|
+
var message: Message;
|
|
298
|
+
message.setAutoTrack(true);
|
|
299
|
+
```
|
|
300
|
+
|
|
301
|
+
### clear
|
|
302
|
+
Clears the reference to the in-memory cached Message object. This function must be called if a Message was saved by calling "Messaging.saveMessage" but no longer needed. Failure to call this function leads to memory leaks.
|
|
303
|
+
|
|
304
|
+
|
|
305
|
+
**Syntax**
|
|
306
|
+
```javascript
|
|
307
|
+
clear();
|
|
308
|
+
```
|
|
309
|
+
|
|
310
|
+
**Example**
|
|
311
|
+
```javascript
|
|
312
|
+
var message: Message;
|
|
313
|
+
message.clear();
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
## Programatically control the display of in-app messages
|
|
317
|
+
App developers can now create a type MessagingDelegate in order to be alerted when specific events occur during the lifecycle of an in-app message.
|
|
318
|
+
|
|
319
|
+
Definition of type MessagingDelegate is:
|
|
320
|
+
```javascript
|
|
321
|
+
type MessagingDelegate = {
|
|
322
|
+
|
|
323
|
+
onShow(message: Message): void;
|
|
324
|
+
|
|
325
|
+
onDismiss(message: Message): void;
|
|
326
|
+
|
|
327
|
+
shouldShowMessage(message: Message): boolean;
|
|
328
|
+
|
|
329
|
+
urlLoaded(url: string, message: Message): void;
|
|
330
|
+
};
|
|
331
|
+
```
|
|
332
|
+
Objects of type MessagingDelegate can be created as shown below:
|
|
333
|
+
```javascript
|
|
334
|
+
const messagingDelegate = {
|
|
335
|
+
|
|
336
|
+
onShow(message: Message) {
|
|
337
|
+
// Action after message is displayed.
|
|
338
|
+
},
|
|
339
|
+
|
|
340
|
+
onDismiss(message: Message) {
|
|
341
|
+
// Action after message is dismissed.
|
|
342
|
+
},
|
|
343
|
+
|
|
344
|
+
shouldShowMessage(message: Message) {
|
|
345
|
+
return true; //Return true to show the Message else return false
|
|
346
|
+
},
|
|
347
|
+
|
|
348
|
+
urlLoaded(url: string, message: Message) {
|
|
349
|
+
// Action after message loads an URL
|
|
350
|
+
}
|
|
351
|
+
};
|
|
352
|
+
```
|
|
353
|
+
|
|
354
|
+
### Controlling when the message should be shown to the end user.
|
|
355
|
+
If a MessagingDelegate has been set, the delegate's shouldShowMessage method will be called prior to displaying an in-app message for which the end user has qualified. The developer is responsible for returning true if the message should be shown, or false if the message should be suppressed.
|
|
356
|
+
|
|
357
|
+
Below is an example of when the developer may choose to suppress an in-app message due to the status of some other workflow within the app:
|
|
358
|
+
```javascript
|
|
359
|
+
function shouldShowMessage(message: Message): boolean {
|
|
360
|
+
if(someOtherWorkflowStatus == "inProgress") {
|
|
361
|
+
return false
|
|
362
|
+
}
|
|
363
|
+
|
|
364
|
+
return true
|
|
365
|
+
}
|
|
366
|
+
```
|
|
367
|
+
|
|
368
|
+
Another option for the developer is to store a reference to the Message object, and call the show() function on it at a later time. App developer also have to call _Messaging.saveMessage(message)_ from _shouldShowMessage_ of MessagingDelegate for caching the Message on the native side of the RN AEPMessaging package.
|
|
369
|
+
Continuing with the above example, the developer has stored the message that was triggered initially, and chooses to show it upon completion of the other workflow:
|
|
370
|
+
|
|
371
|
+
```javascript
|
|
372
|
+
var cachedMessage: Message;
|
|
373
|
+
|
|
374
|
+
function otherWorkflowFinished() {
|
|
375
|
+
anotherWorkflowStatus = "complete";
|
|
376
|
+
cachedMessage.show();
|
|
377
|
+
}
|
|
378
|
+
|
|
379
|
+
function shouldShowMessage(message: Message): boolean {
|
|
380
|
+
if(anotherWorkflowStatus === "inProgress") {
|
|
381
|
+
// store the current message for later use
|
|
382
|
+
Messaging.saveMessage(message);
|
|
383
|
+
cachedMessage = message;
|
|
384
|
+
return false
|
|
385
|
+
}
|
|
386
|
+
|
|
387
|
+
return true
|
|
388
|
+
}
|
|
389
|
+
```
|
|
390
|
+
|
|
391
|
+
**Important:** If the cached message is no longer needed after being used, free up the references to the Message object by calling _message.clearMessage()_ to prevent memory leaks. In above example after displaying the in app message using cached message object if it is no longer needed then it should be cleared as shown below.
|
|
392
|
+
```javascript
|
|
393
|
+
function otherWorkflowFinished() {
|
|
394
|
+
anotherWorkflowStatus = "complete";
|
|
395
|
+
currentMessage.show();
|
|
396
|
+
currentMessage.clearMessage();
|
|
397
|
+
}
|
|
398
|
+
```
|
package/android/build.gradle
CHANGED
|
@@ -2,6 +2,7 @@ buildscript {
|
|
|
2
2
|
repositories {
|
|
3
3
|
google()
|
|
4
4
|
mavenCentral()
|
|
5
|
+
maven { url "https://oss.sonatype.org/content/repositories/snapshots/" }
|
|
5
6
|
}
|
|
6
7
|
|
|
7
8
|
dependencies {
|
|
@@ -29,9 +30,11 @@ android {
|
|
|
29
30
|
repositories {
|
|
30
31
|
google()
|
|
31
32
|
mavenCentral()
|
|
33
|
+
maven { url "https://oss.sonatype.org/content/repositories/snapshots/" }
|
|
32
34
|
}
|
|
33
35
|
|
|
34
36
|
dependencies {
|
|
37
|
+
api "com.adobe.marketing.mobile:optimize:1.+"
|
|
38
|
+
api "com.adobe.marketing.mobile:messaging:1.3.0-beta-3-SNAPSHOT"
|
|
35
39
|
implementation "com.facebook.react:react-native:+"
|
|
36
|
-
api "com.adobe.marketing.mobile:messaging:1.+"
|
|
37
40
|
}
|
|
Binary file
|
|
Binary file
|
|
@@ -10,28 +10,252 @@
|
|
|
10
10
|
*/
|
|
11
11
|
package com.adobe.marketing.mobile.reactnative.messaging;
|
|
12
12
|
|
|
13
|
+
import com.adobe.marketing.mobile.AdobeCallback;
|
|
14
|
+
import com.adobe.marketing.mobile.LoggingMode;
|
|
15
|
+
|
|
16
|
+
import static com.adobe.marketing.mobile.LoggingMode.DEBUG;
|
|
17
|
+
import static com.adobe.marketing.mobile.LoggingMode.VERBOSE;
|
|
18
|
+
|
|
19
|
+
import android.util.Log;
|
|
20
|
+
|
|
21
|
+
import com.adobe.marketing.mobile.Message;
|
|
13
22
|
import com.adobe.marketing.mobile.Messaging;
|
|
23
|
+
import com.adobe.marketing.mobile.MessagingEdgeEventType;
|
|
24
|
+
import com.adobe.marketing.mobile.MobileCore;
|
|
25
|
+
import com.adobe.marketing.mobile.services.ServiceProvider;
|
|
26
|
+
import com.adobe.marketing.mobile.services.ui.FullscreenMessage;
|
|
27
|
+
import com.adobe.marketing.mobile.services.ui.FullscreenMessageDelegate;
|
|
28
|
+
import com.facebook.react.bridge.Arguments;
|
|
14
29
|
import com.facebook.react.bridge.Promise;
|
|
15
30
|
import com.facebook.react.bridge.ReactApplicationContext;
|
|
16
31
|
import com.facebook.react.bridge.ReactContextBaseJavaModule;
|
|
17
32
|
import com.facebook.react.bridge.ReactMethod;
|
|
33
|
+
import com.facebook.react.bridge.WritableMap;
|
|
34
|
+
import com.facebook.react.modules.core.DeviceEventManagerModule;
|
|
35
|
+
|
|
36
|
+
import java.util.HashMap;
|
|
37
|
+
import java.util.Map;
|
|
38
|
+
import java.util.concurrent.CountDownLatch;
|
|
39
|
+
|
|
40
|
+
public final class RCTAEPMessagingModule extends ReactContextBaseJavaModule implements FullscreenMessageDelegate {
|
|
41
|
+
|
|
42
|
+
private static final String TAG = "RCTAEPMessagingModule";
|
|
43
|
+
private final Map<String, Message> messageCache;
|
|
44
|
+
private final ReactApplicationContext reactContext;
|
|
45
|
+
private boolean shouldSaveMessage;
|
|
46
|
+
private boolean shouldShowMessage;
|
|
47
|
+
private CountDownLatch latch = new CountDownLatch(1);
|
|
48
|
+
|
|
49
|
+
public RCTAEPMessagingModule(ReactApplicationContext reactContext) {
|
|
50
|
+
super(reactContext);
|
|
51
|
+
this.reactContext = reactContext;
|
|
52
|
+
this.messageCache = new HashMap<>();
|
|
53
|
+
this.shouldShowMessage = false;
|
|
54
|
+
this.shouldSaveMessage = false;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
@Override
|
|
58
|
+
public String getName() {
|
|
59
|
+
return "AEPMessaging";
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
// Required for rn built in EventEmitter Calls.
|
|
63
|
+
@ReactMethod
|
|
64
|
+
public void addListener(String eventName) {}
|
|
65
|
+
|
|
66
|
+
@ReactMethod
|
|
67
|
+
public void removeListeners(Integer count) {}
|
|
68
|
+
|
|
69
|
+
@ReactMethod
|
|
70
|
+
public void extensionVersion(final Promise promise) {
|
|
71
|
+
MobileCore.log(VERBOSE, TAG, "extensionVersion is called");
|
|
72
|
+
promise.resolve(Messaging.extensionVersion());
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
@ReactMethod
|
|
76
|
+
public void refreshInAppMessages() {
|
|
77
|
+
MobileCore.log(VERBOSE, TAG, "refreshInAppMessages is called");
|
|
78
|
+
Messaging.refreshInAppMessages();
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
@ReactMethod
|
|
82
|
+
public void setMessagingDelegate() {
|
|
83
|
+
MobileCore.log(VERBOSE, TAG, "setMessagingDelegate is called");
|
|
84
|
+
ServiceProvider.getInstance().setMessageDelegate(this);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
@ReactMethod
|
|
88
|
+
public void show(final String messageId) {
|
|
89
|
+
if (messageId != null && messageCache.get(messageId) != null) {
|
|
90
|
+
MobileCore.log(VERBOSE, TAG, String.format("show is called with message id: %s", messageId));
|
|
91
|
+
messageCache.get(messageId).show();
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
@ReactMethod
|
|
96
|
+
public void dismiss(final String messageId, final boolean suppressAutoTrack) {
|
|
97
|
+
if (messageId != null && messageCache.get(messageId) != null) {
|
|
98
|
+
MobileCore.log(VERBOSE, TAG, String.format("dismiss is called with message id: %s and suppressAutoTrack: %b", messageId, suppressAutoTrack));
|
|
99
|
+
messageCache.get(messageId).dismiss(suppressAutoTrack);
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
@ReactMethod
|
|
104
|
+
public void track(final String messageId, final String interaction, final int eventType) {
|
|
105
|
+
if (messageId != null && messageCache.get(messageId) != null) {
|
|
106
|
+
MobileCore.log(VERBOSE, TAG, String.format("track is called with message id: %s, interaction: %s and eventType: %d", messageId, interaction, eventType));
|
|
107
|
+
MessagingEdgeEventType edgeEventType = null;
|
|
108
|
+
switch (eventType) {
|
|
109
|
+
case 0:
|
|
110
|
+
edgeEventType = MessagingEdgeEventType.IN_APP_DISMISS;
|
|
111
|
+
break;
|
|
112
|
+
case 1:
|
|
113
|
+
edgeEventType = MessagingEdgeEventType.IN_APP_INTERACT;
|
|
114
|
+
break;
|
|
115
|
+
case 2:
|
|
116
|
+
edgeEventType = MessagingEdgeEventType.IN_APP_TRIGGER;
|
|
117
|
+
break;
|
|
118
|
+
case 3:
|
|
119
|
+
edgeEventType = MessagingEdgeEventType.IN_APP_DISPLAY;
|
|
120
|
+
break;
|
|
121
|
+
case 4:
|
|
122
|
+
edgeEventType = MessagingEdgeEventType.PUSH_APPLICATION_OPENED;
|
|
123
|
+
break;
|
|
124
|
+
case 5:
|
|
125
|
+
edgeEventType = MessagingEdgeEventType.PUSH_CUSTOM_ACTION;
|
|
126
|
+
break;
|
|
127
|
+
default:
|
|
128
|
+
break;
|
|
129
|
+
}
|
|
130
|
+
if (edgeEventType != null) {
|
|
131
|
+
messageCache.get(messageId).track(interaction, edgeEventType);
|
|
132
|
+
} else {
|
|
133
|
+
MobileCore.log(DEBUG, TAG, String.format("Unable to track interaction (%s) because edgeEventType (%d) is invalid ", interaction, eventType));
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
@ReactMethod
|
|
139
|
+
public void handleJavascriptMessage(final String messageId, final String messageName, final Promise promise) {
|
|
140
|
+
if (messageId != null && messageCache.get(messageId) != null) {
|
|
141
|
+
MobileCore.log(VERBOSE, TAG, String.format("handleJavascriptMessage is called with message id: %s and messageName: %s", messageId, messageName));
|
|
142
|
+
messageCache.get(messageId).handleJavascriptMessage(messageName, new AdobeCallback<String>() {
|
|
143
|
+
@Override
|
|
144
|
+
public void call(final String s) {
|
|
145
|
+
if (s != null) {
|
|
146
|
+
promise.resolve(s);
|
|
147
|
+
} else {
|
|
148
|
+
promise.reject("error", "error in handling javascriptMessage " + messageName);
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
});
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
@ReactMethod
|
|
156
|
+
public void clear(final String messageId) {
|
|
157
|
+
if (messageId != null) {
|
|
158
|
+
MobileCore.log(VERBOSE, TAG, String.format("clear is called with message id: %s", messageId));
|
|
159
|
+
messageCache.remove(messageId);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
@ReactMethod
|
|
164
|
+
public void setAutoTrack(final String messageId, final boolean autoTrack) {
|
|
165
|
+
if (messageId != null && messageCache.get(messageId) != null) {
|
|
166
|
+
MobileCore.log(VERBOSE, TAG, String.format("setAutoTrack is called with message id: %s and autoTrack: %b", messageId, autoTrack));
|
|
167
|
+
messageCache.get(messageId).autoTrack = autoTrack;
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
@ReactMethod(isBlockingSynchronousMethod = true)
|
|
172
|
+
public void shouldShowMessage(final boolean shouldShowMessage, final boolean shouldSaveMessage) {
|
|
173
|
+
MobileCore.log(VERBOSE, TAG, String.format("shouldShowMessage is called with message id: %b and shouldSaveMessage: %b", shouldShowMessage, shouldSaveMessage));
|
|
174
|
+
this.shouldShowMessage = shouldShowMessage;
|
|
175
|
+
this.shouldSaveMessage = shouldSaveMessage;
|
|
176
|
+
latch.countDown();
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
//Messaging Delegate functions
|
|
180
|
+
@Override
|
|
181
|
+
public void onShow(final FullscreenMessage fullscreenMessage) {
|
|
182
|
+
MobileCore.log(VERBOSE, TAG, "onShow is called");
|
|
183
|
+
final Message message = (Message) fullscreenMessage.getParent();
|
|
184
|
+
if (message != null) {
|
|
185
|
+
Map<String, String> data = new HashMap<>();
|
|
186
|
+
data.put("id", message.id);
|
|
187
|
+
data.put("autoTrack", String.valueOf(message.autoTrack));
|
|
188
|
+
emitEvent("onShow", data);
|
|
189
|
+
}
|
|
190
|
+
}
|
|
18
191
|
|
|
19
|
-
|
|
192
|
+
@Override
|
|
193
|
+
public void onDismiss(final FullscreenMessage fullscreenMessage) {
|
|
194
|
+
MobileCore.log(VERBOSE, TAG, "onDismiss is called");
|
|
195
|
+
final Message message = (Message) fullscreenMessage.getParent();
|
|
196
|
+
if (message != null) {
|
|
197
|
+
Map<String, String> data = new HashMap<>();
|
|
198
|
+
data.put("id", message.id);
|
|
199
|
+
data.put("autoTrack", String.valueOf(message.autoTrack));
|
|
200
|
+
emitEvent("onDismiss", data);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
20
203
|
|
|
21
|
-
|
|
204
|
+
@Override
|
|
205
|
+
public boolean shouldShowMessage(final FullscreenMessage fullscreenMessage) {
|
|
206
|
+
MobileCore.log(VERBOSE, TAG, "shouldShowMessage is called");
|
|
207
|
+
final Message message = (Message) fullscreenMessage.getParent();
|
|
208
|
+
if (message != null) {
|
|
209
|
+
Map<String, String> data = new HashMap<>();
|
|
210
|
+
data.put("id", message.id);
|
|
211
|
+
data.put("autoTrack", String.valueOf(message.autoTrack));
|
|
212
|
+
emitEvent("shouldShowMessage", data);
|
|
213
|
+
//Latch stops the thread until the shouldShowMessage value is received from the JS side on thread dedicated to run JS code. The function called from JS that resumes the thread is "shouldShowMessage".
|
|
214
|
+
MobileCore.log(VERBOSE, TAG, "shouldShowMessage: Thread is locked.");
|
|
215
|
+
try {
|
|
216
|
+
latch.await();
|
|
217
|
+
} catch (final InterruptedException e) {
|
|
218
|
+
MobileCore.log(LoggingMode.ERROR, TAG, String.format("CountDownLatch await Interrupted: (%s)", e.getLocalizedMessage()));
|
|
219
|
+
}
|
|
220
|
+
MobileCore.log(VERBOSE, TAG, "shouldShowMessage: Thread is resumed.");
|
|
221
|
+
if (shouldSaveMessage) {
|
|
222
|
+
messageCache.put(message.id, message);
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
return shouldShowMessage;
|
|
226
|
+
}
|
|
22
227
|
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
228
|
+
@Override
|
|
229
|
+
public boolean overrideUrlLoad(FullscreenMessage fullscreenMessage, String s) {
|
|
230
|
+
MobileCore.log(VERBOSE, TAG, String.format("overrideUrlLoad is called with url: (%s)", s));
|
|
231
|
+
final Message message = (Message) fullscreenMessage.getParent();
|
|
232
|
+
if (message != null) {
|
|
233
|
+
Map<String, String> data = new HashMap<>();
|
|
234
|
+
data.put("id", message.id);
|
|
235
|
+
data.put("autoTrack", String.valueOf(message.autoTrack));
|
|
236
|
+
data.put("url", s);
|
|
237
|
+
emitEvent("shouldShowMessage", data);
|
|
238
|
+
emitEvent("urlLoaded", data);
|
|
239
|
+
}
|
|
240
|
+
return true;
|
|
241
|
+
}
|
|
27
242
|
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
243
|
+
@Override
|
|
244
|
+
public void onShowFailure() {
|
|
245
|
+
MobileCore.log(VERBOSE, TAG, "onShowFailure is called.");
|
|
246
|
+
}
|
|
32
247
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
248
|
+
/**
|
|
249
|
+
* Emits an event along with data to be handled by the Javascript
|
|
250
|
+
*
|
|
251
|
+
* @param name event name
|
|
252
|
+
* @param data data sent along with event
|
|
253
|
+
*/
|
|
254
|
+
private void emitEvent(final String name, final Map<String, String> data) {
|
|
255
|
+
WritableMap eventData = Arguments.createMap();
|
|
256
|
+
for (final Map.Entry<String, String> entry : data.entrySet()) {
|
|
257
|
+
eventData.putString(entry.getKey(), entry.getValue());
|
|
258
|
+
}
|
|
259
|
+
reactContext.getJSModule(DeviceEventManagerModule.RCTDeviceEventEmitter.class).emit(name, eventData);
|
|
260
|
+
}
|
|
37
261
|
}
|
|
@@ -9,9 +9,12 @@
|
|
|
9
9
|
governing permissions and limitations under the License.
|
|
10
10
|
*/
|
|
11
11
|
|
|
12
|
-
|
|
13
|
-
|
|
12
|
+
#import <React/RCTBridgeModule.h>
|
|
13
|
+
#import <Foundation/Foundation.h>
|
|
14
|
+
#import <React/RCTEventEmitter.h>
|
|
15
|
+
#import <React/RCTBridgeModule.h>
|
|
16
|
+
@import AEPServices;
|
|
14
17
|
|
|
15
|
-
@interface RCTAEPMessaging :
|
|
18
|
+
@interface RCTAEPMessaging : RCTEventEmitter <RCTBridgeModule, AEPMessagingDelegate>
|
|
16
19
|
|
|
17
20
|
@end
|