diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 30ee764a..95e97add 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -33,7 +33,7 @@ jobs: UNITY_SERIAL: ${{ secrets.UNITY_SERIAL }} with: targetPlatform: iOS - - uses: actions/upload-artifact@v2 + - uses: actions/upload-artifact@v4 with: name: Build path: build @@ -76,7 +76,7 @@ jobs: # After echo "Disk space after:" df -h - - uses: actions/upload-artifact@v2 + - uses: actions/upload-artifact@v4 if: always() with: name: Test results for ${{ matrix.testMode }} diff --git a/Assets/AppsFlyer/AppsFlyer.cs b/Assets/AppsFlyer/AppsFlyer.cs index 1d97967d..80671744 100644 --- a/Assets/AppsFlyer/AppsFlyer.cs +++ b/Assets/AppsFlyer/AppsFlyer.cs @@ -6,7 +6,7 @@ namespace AppsFlyerSDK { public class AppsFlyer : MonoBehaviour { - public static readonly string kAppsFlyerPluginVersion = "6.15.3"; + public static readonly string kAppsFlyerPluginVersion = "6.16.0"; public static string CallBackObjectName = null; private static EventHandler onRequestResponse; private static EventHandler onInAppResponse; diff --git a/Assets/AppsFlyer/Editor/AppsFlyerDependencies.xml b/Assets/AppsFlyer/Editor/AppsFlyerDependencies.xml index 04188cc3..34e64fa5 100644 --- a/Assets/AppsFlyer/Editor/AppsFlyerDependencies.xml +++ b/Assets/AppsFlyer/Editor/AppsFlyerDependencies.xml @@ -2,16 +2,16 @@ - + - + - + diff --git a/Assets/AppsFlyer/Plugins/iOS/AppsFlyeriOSWrapper.mm b/Assets/AppsFlyer/Plugins/iOS/AppsFlyeriOSWrapper.mm index 8d91cc56..da6cdec5 100644 --- a/Assets/AppsFlyer/Plugins/iOS/AppsFlyeriOSWrapper.mm +++ b/Assets/AppsFlyer/Plugins/iOS/AppsFlyeriOSWrapper.mm @@ -18,7 +18,7 @@ static void unityCallBack(NSString* objectName, const char* method, const char* const void _startSDK(bool shouldCallback, const char* objectName) { [[AppsFlyerLib shared] setPluginInfoWith: AFSDKPluginUnity - pluginVersion:@"6.15.3" + pluginVersion:@"6.16.0" additionalParams:nil]; startRequestObjectName = stringFromChar(objectName); AppsFlyeriOSWarpper.didCallStart = YES; diff --git a/Assets/AppsFlyer/package.json b/Assets/AppsFlyer/package.json index b1292ede..70853e47 100644 --- a/Assets/AppsFlyer/package.json +++ b/Assets/AppsFlyer/package.json @@ -2,7 +2,7 @@ "name": "appsflyer-unity-plugin", "displayName": "AppsFlyer", "description": "AppsFlyer Unity plugin", - "version": "6.15.2", + "version": "6.15.3", "unity": "2019.4", "license": "MIT" } diff --git a/CHANGELOG.md b/CHANGELOG.md index b2973816..d51a50df 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,7 @@ # Versions +## v6.15.3 +* Fix logAdRevenue - revenue value will not be rounded + ## v6.15.2 * Update iOS SDK version - 6.15.2 diff --git a/android-unity-wrapper/app/build.gradle b/android-unity-wrapper/app/build.gradle index 7492e611..e4e8331d 100644 --- a/android-unity-wrapper/app/build.gradle +++ b/android-unity-wrapper/app/build.gradle @@ -1,13 +1,14 @@ apply plugin: 'com.android.application' android { - compileSdkVersion 29 + namespace 'com.appsflyer.unitywrapper' + compileSdkVersion 33 defaultConfig { applicationId "com.appsflyer.unitywrapper" minSdkVersion 16 - targetSdkVersion 29 + targetSdkVersion 32 versionCode 1 versionName "1.0" diff --git a/android-unity-wrapper/app/src/main/AndroidManifest.xml b/android-unity-wrapper/app/src/main/AndroidManifest.xml index fdd692cf..19929d3d 100644 --- a/android-unity-wrapper/app/src/main/AndroidManifest.xml +++ b/android-unity-wrapper/app/src/main/AndroidManifest.xml @@ -1,5 +1,4 @@ - + - uploadArchives { - repositories { - mavenDeployer { - beforeDeployment { MavenDeployment deployment -> signing.signPom(deployment) } - pom.groupId = GROUP - pom.artifactId = POM_ARTIFACT_ID - pom.version = VERSION_NAME - repository(url: "https://oss.sonatype.org/service/local/staging/deploy/maven2/") { - authentication(userName: ossrhUsername, password: ossrhPassword) - } - snapshotRepository(url: "https://oss.sonatype.org/content/repositories/snapshots/") { - authentication(userName: ossrhUsername, password: ossrhPassword) - } - pom.project { - name POM_NAME - packaging POM_PACKAGING - description POM_DESCRIPTION - url POM_URL - scm { - url POM_SCM_URL - connection POM_SCM_CONNECTION - developerConnection POM_SCM_DEV_CONNECTION - } +def getReleaseRepositoryUrl() { + return hasProperty('RELEASE_REPOSITORY_URL') ? RELEASE_REPOSITORY_URL + : "https://oss.sonatype.org/service/local/staging/deploy/maven2/" +} + +def getSnapshotRepositoryUrl() { + return hasProperty('SNAPSHOT_REPOSITORY_URL') ? SNAPSHOT_REPOSITORY_URL + : "https://oss.sonatype.org/content/repositories/snapshots/" +} + +android { + publishing { + singleVariant("release") { + // if you don't want sources/javadoc, remove these lines + withJavadocJar() + } + } +} + +afterEvaluate { + publishing { + publications { + release(MavenPublication) { + // The coordinates of the library + groupId = GROUP + artifactId = POM_ARTIFACT_ID + version = VERSION_NAME + + // Artifacts to publish + artifact("$buildDir/outputs/aar/${project.name}-release.aar") + + // Configure POM metadata + pom { + name.set(POM_NAME) + description.set(POM_DESCRIPTION) + url.set(POM_URL) + licenses { license { - name POM_LICENCE_NAME - url POM_LICENCE_URL - distribution POM_LICENCE_DIST + name.set(POM_LICENCE_NAME) + url.set(POM_LICENCE_URL) + distribution.set(POM_LICENCE_DIST) } } + developers { developer { - id POM_DEVELOPER_ID - name POM_DEVELOPER_NAME + id.set(POM_DEVELOPER_ID) + name.set(POM_DEVELOPER_NAME) } } + + scm { + connection.set(POM_SCM_CONNECTION) + developerConnection.set(POM_SCM_DEV_CONNECTION) + url.set(POM_SCM_URL) + } + } + + // Add dependencies to the POM + pom.withXml { + def dependenciesNode = asNode().appendNode('dependencies') + configurations.implementation.allDependencies.each { dependency -> + def dependencyNode = dependenciesNode.appendNode('dependency') + dependencyNode.appendNode('groupId', dependency.group ?: '') + dependencyNode.appendNode('artifactId', dependency.name) + dependencyNode.appendNode('version', dependency.version ?: '') + } } } } - } - signing { - required { isReleaseBuild() && gradle.taskGraph.hasTask("uploadArchives") } - sign configurations.archives - } - task androidJavadocs(type: Javadoc) { - classpath += project.files(android.getBootClasspath().join(File.pathSeparator)) - if (JavaVersion.current().isJava8Compatible()) { - allprojects { - tasks.withType(Javadoc) { options.addStringOption('Xdoclint:none', '-quiet') } + + repositories { + maven { + name = "sonatype" + url = isReleaseBuild() ? getReleaseRepositoryUrl() : getSnapshotRepositoryUrl() + + credentials { + username = ossrhUsername + password = ossrhPassword + } } } } - task androidJavadocsJar(type: Jar, dependsOn: androidJavadocs) { - archiveClassifier = 'javadoc' - from androidJavadocs.destinationDir - } - task androidSourcesJar(type: Jar) { - classifier = 'sources' - from android.sourceSets.main.java.sourceFiles + + signing { + required { isReleaseBuild() && gradle.taskGraph.hasTask("publish") } + sign publishing.publications.release } - artifacts { archives androidJavadocsJar } +// task androidJavadocs(type: Javadoc) { +// classpath += project.files(android.getBootClasspath().join(File.pathSeparator)) +// if (JavaVersion.current().isJava8Compatible()) { +// allprojects { +// tasks.withType(Javadoc) { options.addStringOption('Xdoclint:none', '-quiet') } +// } +// } +// } +// task androidJavadocsJar(type: Jar, dependsOn: androidJavadocs) { +// archiveClassifier = 'javadoc' +// from androidJavadocs.destinationDir +// } +// task androidSourcesJar(type: Jar) { +// classifier = 'sources' +// from android.sourceSets.main.java.sourceFiles +// } +// artifacts { archives androidJavadocsJar } } \ No newline at end of file diff --git a/android-unity-wrapper/unitywrapper/src/main/AndroidManifest.xml b/android-unity-wrapper/unitywrapper/src/main/AndroidManifest.xml index 388ec10e..c4e6c98d 100644 --- a/android-unity-wrapper/unitywrapper/src/main/AndroidManifest.xml +++ b/android-unity-wrapper/unitywrapper/src/main/AndroidManifest.xml @@ -1,2 +1 @@ - + diff --git a/android-unity-wrapper/unitywrapper/src/main/java/com/appsflyer/unity/AppsFlyerAndroidWrapper.java b/android-unity-wrapper/unitywrapper/src/main/java/com/appsflyer/unity/AppsFlyerAndroidWrapper.java index c55437e4..e45dbbf8 100644 --- a/android-unity-wrapper/unitywrapper/src/main/java/com/appsflyer/unity/AppsFlyerAndroidWrapper.java +++ b/android-unity-wrapper/unitywrapper/src/main/java/com/appsflyer/unity/AppsFlyerAndroidWrapper.java @@ -45,7 +45,7 @@ public class AppsFlyerAndroidWrapper { private static final String ON_DEEPLINKING = "onDeepLinking"; private static final String START_REQUEST_CALLBACK = "requestResponseReceived"; private static final String IN_APP_RESPONSE_CALLBACK = "inAppResponseReceived"; - private static final String PLUGIN_VERSION = "6.15.3"; + private static final String PLUGIN_VERSION = "6.16.0"; private static final long DDL_TIMEOUT_DEFAULT = 3000; private static AppsFlyerConversionListener conversionListener; private static String devkey = ""; diff --git a/appsflyer-unity-plugin-6.15.2.unitypackage b/appsflyer-unity-plugin-6.15.2.unitypackage deleted file mode 100644 index cf7430ad..00000000 Binary files a/appsflyer-unity-plugin-6.15.2.unitypackage and /dev/null differ diff --git a/appsflyer-unity-plugin-6.15.3.unitypackage b/appsflyer-unity-plugin-6.15.3.unitypackage new file mode 100644 index 00000000..df7648c8 Binary files /dev/null and b/appsflyer-unity-plugin-6.15.3.unitypackage differ diff --git a/deploy/build_unity_package.sh b/deploy/build_unity_package.sh index b5dd2006..f99d99d6 100644 --- a/deploy/build_unity_package.sh +++ b/deploy/build_unity_package.sh @@ -4,7 +4,7 @@ echo "Start Build for appsflyer-unity-plugin.unitypackage" DEPLOY_PATH=outputs UNITY_PATH="/Applications/Unity/Unity.app/Contents/MacOS/Unity" -PACKAGE_NAME="appsflyer-unity-plugin-6.15.2.unitypackage" +PACKAGE_NAME="appsflyer-unity-plugin-6.15.3.unitypackage" mkdir -p $DEPLOY_PATH #move external dependency manager @@ -23,7 +23,7 @@ mv external-dependency-manager-1.2.177.unitypackage .. Assets \ $PWD/$DEPLOY_PATH/$PACKAGE_NAME \ -quit \ -&& echo "package exported successfully to outputs/appsflyer-unity-plugin-6.15.2.unitypackage" \ +&& echo "package exported successfully to outputs/appsflyer-unity-plugin-6.15.3.unitypackage" \ || echo "Failed to export package. See create_unity_core.log for more info." diff --git a/deploy/strict_mode_build_package.sh b/deploy/strict_mode_build_package.sh index ae276e90..2b24e7e0 100644 --- a/deploy/strict_mode_build_package.sh +++ b/deploy/strict_mode_build_package.sh @@ -5,7 +5,7 @@ echo "Start Build for appsflyer-unity-plugin.unitypackage. Strict Mode." DEPLOY_PATH=outputs UNITY_PATH="/Applications/Unity/Unity.app/Contents/MacOS/Unity" - PACKAGE_NAME="appsflyer-unity-plugin-strict-mode-6.15.2.unitypackage" + PACKAGE_NAME="appsflyer-unity-plugin-strict-mode-6.15.3.unitypackage" mkdir -p $DEPLOY_PATH #move external dependency manager @@ -37,7 +37,7 @@ echo "Commenting out functions. Done." Assets \ $PWD/$DEPLOY_PATH/$PACKAGE_NAME \ -quit \ - && echo "package exported successfully to outputs/appsflyer-unity-plugin-strict-mode-6.15.2.unitypackage" \ + && echo "package exported successfully to outputs/appsflyer-unity-plugin-strict-mode-6.15.3.unitypackage" \ || echo "Failed to export package. See create_unity_core.log for more info." diff --git a/docs/InAppEvents.md b/docs/InAppEvents.md index 7cbba08f..fa646b08 100644 --- a/docs/InAppEvents.md +++ b/docs/InAppEvents.md @@ -43,6 +43,10 @@ AppsFlyer.sendEvent(AFInAppEvents.PURCHASE, eventValues); ## Logging revenue +> 📘 Note +> +> For events with **revenue**, including in-app purchases, subscriptions, and ad revenue events, AppsFlyer customers with an ROI360 subscription should avoid using the `AFInAppEvents.REVENUE`(`af_revenue`) parameter in their in-app events. Doing so can result in duplicate revenue being reported. Instead, they should utilize the [purchase connector](https://dev.appsflyer.com/hc/docs/purchaseconnectorunity) and the [ad revenue SDK API](https://dev.appsflyer.com/hc/docs/ad-revenue-unity). + You can send revenue with any in-app event. Use the `AFInAppEvents.REVENUE` event parameter to include revenue in the in-app event. You can populate it with any numeric value, positive or negative. The revenue value should not contain comma separators, currency signs, or text. A revenue event should be similar to 1234.56, for example. diff --git a/docs/Installation.md b/docs/Installation.md index 41563215..1f55b85a 100644 --- a/docs/Installation.md +++ b/docs/Installation.md @@ -56,7 +56,7 @@ Add this line for the latest version of the regular mode 2. Download and add the required Android dependencies to the Assets/Plugins/Android folder: 1. [AppsFlyer Android SDK](https://repo1.maven.org/maven2/com/appsflyer/af-android-sdk/6.15.0/af-android-sdk-6.15.0.aar) - 2. [AppsFlyer Unity Wrapper](https://repo1.maven.org/maven2/com/appsflyer/unity-wrapper/6.15.2/unity-wrapper-6.15.2.aar) + 2. [AppsFlyer Unity Wrapper](https://repo1.maven.org/maven2/com/appsflyer/unity-wrapper/6.15.3/unity-wrapper-6.15.3.aar) 3. [Google Installreferrer library](https://mvnrepository.com/artifact/com.android.installreferrer/installreferrer/2.1) 3. Download and add the required iOS dependencies to the Assets/Plugins/iOS/AppsFlyer folder: 1. [Download](https://github.com/AppsFlyerSDK/AppsFlyerFramework/releases/tag/6.14.4) the iOS SDK as a static library `AppsFlyerLib.xcframework.zip` diff --git a/docs/ad-revenue-unity.md b/docs/ad-revenue-unity.md index 0b8355e3..eff0c3c7 100644 --- a/docs/ad-revenue-unity.md +++ b/docs/ad-revenue-unity.md @@ -30,9 +30,9 @@ When an impression with revenue occurs, invoke the [`logAdRevenue`](doc:api#loga ```c# Dictionary additionalParams = new Dictionary(); additionalParams.Add(AdRevenueScheme.COUNTRY, "USA"); -additionalParams.Add(AFAdRevenueEvent.AD_UNIT, "89b8c0159a50ebd1"); -additionalParams.Add(AFAdRevenueEvent.AD_TYPE, "Banner"); -additionalParams.Add(AFAdRevenueEvent.PLACEMENT, "place"); +additionalParams.Add(AdRevenueScheme.AD_UNIT, "89b8c0159a50ebd1"); +additionalParams.Add(AdRevenueScheme.AD_TYPE, "Banner"); +additionalParams.Add(AdRevenueScheme.PLACEMENT, "place"); var logRevenue = new AFAdRevenueData("monetizationNetworkEx", MediationNetwork.GoogleAdMob, "USD", 0.99); AppsFlyer.logAdRevenue(logRevenue, additionalParams); ``` diff --git a/docs/purchase-connector.md b/docs/purchase-connector.md new file mode 100644 index 00000000..c1bb6877 --- /dev/null +++ b/docs/purchase-connector.md @@ -0,0 +1,179 @@ +--- +title: "Purchase connector" +slug: "purchase-connector-unity" +category: 5f9705393c689a065c409b23 +parentDoc: 6370c9e2441a4504d6bca3bd +excerpt: "Used to validate and report in-app purchase and subscription revenue events" +hidden: false +order: 13 +--- + +## Overview + +The AppsFlyer ROI360 purchase connector is used to validate and report in-app purchase and subscription revenue events. It’s part of the ROI360 in-app purchase and subscription revenue measurement solution. + +- Using the purchase connector requires an ROI360 subscription. +- If you use this in-app purchase and subscription revenue measurement solution, you shouldn’t send [in-app purchase events](https://dev.appsflyer.com/hc/docs/inappevents) with revenue or execute [`validateAndLogInAppPurchase`](https://dev.appsflyer.com/hc/docs/validate-and-log-purchase-ios), as doing so results in duplicate revenue being reported. +- Before implementing the purchase connector, the ROI360 in-app purchase and subscription revenue measurement needs to be integrated with Google Play and the App Store. [See instructions (steps 1 and 2)](https://support.appsflyer.com/hc/en-us/articles/7459048170769) + +## Prerequisites + +- StoreKit SDK v1 +- iOS version 9 and higher. +- Unity AppsFlyer plugin **6.12.2** and higher. +- Unity version **2020.3** and higher. +- Google Billing Play version **5.x.x** and **6.x.x** + +To use the module with earlier Unity AppsFlyer plugin versions, check the previous versions of this module, for instance, **v1.0.0** supports versions **6.8.1** and higher. + +## Adding The Connector To Your Project + +1. Clone / download [Purchase Connector repository](https://github.com/AppsFlyerSDK/appsflyer-unity-purchase-connector). +2. [Import](https://docs.unity3d.com/Manual/AssetPackages.html) appsflyer-unity-purchase-connector-x.x.x.unitypackage into your Unity project. + - Go to Assets >> Import Package >> Custom Package + - Select appsflyer-unity-adrepurchase-connector-x.x.x.unitypackage. + +**Note:** You must have the [AppsFlyer Unity plugin](https://github.com/AppsFlyerSDK/appsflyer-unity-plugin) already in your project. In addition, make sure to init AppsFlyer SDK before Purchase Connector. + +## ProGuard Rules + +_Android Only_ - If you are using ProGuard, add the following keep rules to your `proguard-rules.pro` file: + +```groovy +-keep class com.appsflyer.** { *; } +-keep class kotlin.jvm.internal.Intrinsics{ *; } +-keep class kotlin.collections.**{ *; } +-keep class kotlin.Result$Companion { *; } +``` + +## Strict Mode + +The module supports a Strict Mode which completely removes the IDFA collection functionality and AdSupport framework dependencies. Use the Strict Mode when developing apps for kids, for example. +Make sure to use strict mode module with AppsFlyer Unity strict mode plugin. + +## Basic Integration + +> _Note: before the implementation of the Purchase connector, please make sure to set up AppsFlyer `appId` and `devKey`_ + +### Set up Purchase Connector + +> Notes: +> +> - The **AppsFlyerPurchaseConnector.init** api initialized the connector for both iOS and Android. However, the store parameter is only for Android stores. +> - You only need to call the API **AppsFlyerPurchaseConnector.init** once with the android store as parameter and it will work for both platforms. +> - For now, the only Android store available is Google. + +```c# + using AppsFlyerSDK; + using AppsFlyerConnector; + +// Default SDK Implementation + AppsFlyer.initSDK(devKey, appID, getConversionData ? this : null); + +// Purchase connector implementation + AppsFlyerPurchaseConnector.init(this, AppsFlyerConnector.Store.GOOGLE); + AppsFlyerPurchaseConnector.setIsSandbox(true); + AppsFlyerPurchaseConnector.setAutoLogPurchaseRevenue(AppsFlyerAutoLogPurchaseRevenueOptions.AppsFlyerAutoLogPurchaseRevenueOptionsAutoRenewableSubscriptions, AppsFlyerAutoLogPurchaseRevenueOptions.AppsFlyerAutoLogPurchaseRevenueOptionsInAppPurchases); + AppsFlyerPurchaseConnector.build(); + +``` + +### Log Auto-Renewable Subscriptions and In-App Purchases + +Enables automatic logging of In-App purchases and Auto-renewable subscriptions. + +```c# +AppsFlyerPurchaseConnector.setAutoLogPurchaseRevenue(AppsFlyerAutoLogPurchaseRevenueOptions.AppsFlyerAutoLogPurchaseRevenueOptionsAutoRenewableSubscriptions, AppsFlyerAutoLogPurchaseRevenueOptions.AppsFlyerAutoLogPurchaseRevenueOptionsInAppPurchases); +``` + +> _Note: if `autoLogPurchaseRevenue` has not been set, it is disabled by default. The value is an option set, so you can choose what kind of user purchases you want to observe._ + +### Get purchase validation callback + +- In order to receive purchase validation event callbacks, you should conform to the purchase validation listener and implement the callback + +```c# +AppsFlyerPurchaseConnector.setPurchaseRevenueValidationListeners(true); +/* ... */ + +public void didReceivePurchaseRevenueValidationInfo(string validationInfo) +{ + AppsFlyer.AFLog("didReceivePurchaseRevenueValidationInfo", validationInfo); + // deserialize the string as a dictionnary, easy to manipulate + Dictionary dictionary = AFMiniJSON.Json.Deserialize(validationInfo) as Dictionary; + + // if the platform is Android, you can create an object from the dictionnary +#if UNITY_ANDROID + if (dictionary.ContainsKey("productPurchase") && dictionary["productPurchase"] != null) + { + // Create an object from the JSON string. + InAppPurchaseValidationResult iapObject = JsonUtility.FromJson(validationInfo); + } elif (dictionary.ContainsKey("subscriptionPurchase") && dictionary["subscriptionPurchase"] != null) { + SubscriptionValidationResult iapObject = JsonUtility.FromJson(validationInfo); + #endif + +} +``` + +### Start Observing Transactions + +`startObservingTransactions` should be called to start observing transactions. + +```c# + AppsFlyerPurchaseConnector.startObservingTransactions(); +``` + +### Stop Observing Transactions + +To stop observing transactions, you need to call `stopObservingTransactions`. + +```c# + AppsFlyerPurchaseConnector.stopObservingTransactions(); +``` + +> _Note: if you called `stopObservingTransactions` API, you should set `autoLogPurchaseRevenue` value before you call `startObservingTransactions` next time._ +> _Note: The Purchase Connector for Unity currently does not support adding Custom Parameters to purchase events_ + +## Testing the implementation in Sandbox + +To set the sandbox environnment, you need to set `isSandbox` to true.
+For iOS, it will allow you to test in Xcode environment on a real device with TestFlight sandbox account.
+And for Android, it should be used while testing your [Google Play Billing Library integration](https://developer.android.com/google/play/billing/test). + +```c# + AppsFlyerPurchaseConnector.setIsSandbox(true); +``` + +> _IMPORTANT NOTE: Before releasing your app to production please be sure to remove `isSandbox` or set it to `false`. If the production purchase event will be sent in sandbox mode, your event will not be validated properly! _ + +*** + +## Full Code Example + +```c# +using System.Collections; +using System.Collections.Generic; +using UnityEngine; +using AppsFlyerSDK; +using UnityEngine.UI; +using AppsFlyerConnector; + +void Start() + { + AppsFlyer.initSDK(devKey, appID, getConversionData ? this : null); + AppsFlyer.setIsDebug(isDebug); + AppsFlyerPurchaseConnector.init(this, AppsFlyerConnector.Store.GOOGLE); + AppsFlyerPurchaseConnector.setIsSandbox(true); + AppsFlyerPurchaseConnector.setAutoLogPurchaseRevenue(AppsFlyerAutoLogPurchaseRevenueOptions.AppsFlyerAutoLogPurchaseRevenueOptionsAutoRenewableSubscriptions, AppsFlyerAutoLogPurchaseRevenueOptions.AppsFlyerAutoLogPurchaseRevenueOptionsInAppPurchases); + AppsFlyerPurchaseConnector.setPurchaseRevenueValidationListeners(true); + AppsFlyerPurchaseConnector.build(); + AppsFlyerPurchaseConnector.startObservingTransactions(); + AppsFlyer.startSDK(); + } + + public void didReceivePurchaseRevenueValidationInfo(string validationInfo) + { + AppsFlyer.AFLog("didReceivePurchaseRevenueValidationInfo", validationInfo); + } + +``` diff --git a/strict-mode-sdk/appsflyer-unity-plugin-strict-mode-6.15.2.unitypackage b/strict-mode-sdk/appsflyer-unity-plugin-strict-mode-6.15.2.unitypackage deleted file mode 100644 index ffc543fd..00000000 Binary files a/strict-mode-sdk/appsflyer-unity-plugin-strict-mode-6.15.2.unitypackage and /dev/null differ diff --git a/strict-mode-sdk/appsflyer-unity-plugin-strict-mode-6.15.3.unitypackage b/strict-mode-sdk/appsflyer-unity-plugin-strict-mode-6.15.3.unitypackage new file mode 100644 index 00000000..288329bb Binary files /dev/null and b/strict-mode-sdk/appsflyer-unity-plugin-strict-mode-6.15.3.unitypackage differ