diff --git a/splitio/lib/splitio.dart b/splitio/lib/splitio.dart index 3db1151..f20b066 100644 --- a/splitio/lib/splitio.dart +++ b/splitio/lib/splitio.dart @@ -121,6 +121,14 @@ class Splitio { return _platform.split(splitName: splitName); } + Future getUserConsent() async { + return _platform.getUserConsent(); + } + + Future setUserConsent(bool enabled) async { + return _platform.setUserConsent(enabled); + } + Future _init() { return _platform.init( apiKey: _sdkKey, diff --git a/splitio/pubspec.yaml b/splitio/pubspec.yaml index 650fcbc..1437b31 100644 --- a/splitio/pubspec.yaml +++ b/splitio/pubspec.yaml @@ -19,9 +19,15 @@ flutter: dependencies: flutter: sdk: flutter - splitio_android: ^0.1.3 - splitio_ios: ^0.1.3 - splitio_platform_interface: ^1.1.0 +# splitio_android: ^0.1.3 + splitio_android: + path: ../splitio_android +# splitio_ios: ^0.1.3 + splitio_ios: + path: ../splitio_ios +# splitio_platform_interface: ^1.1.0 + splitio_platform_interface: + path: ../splitio_platform_interface dev_dependencies: flutter_test: diff --git a/splitio/test/splitio_platform_stub.dart b/splitio/test/splitio_platform_stub.dart index 29f1526..369cc83 100644 --- a/splitio/test/splitio_platform_stub.dart +++ b/splitio/test/splitio_platform_stub.dart @@ -339,4 +339,19 @@ class SplitioPlatformStub return Future.value(true); } + + @override + Future getUserConsent() { + methodName = 'getUserConsent'; + + return Future.value(UserConsent.granted); + } + + @override + Future setUserConsent(bool enabled) { + methodName = 'setUserConsent'; + methodArguments['value'] = enabled; + + return Future.value(null); + } } diff --git a/splitio/test/splitio_test.dart b/splitio/test/splitio_test.dart index ac227f2..87ad6e4 100644 --- a/splitio/test/splitio_test.dart +++ b/splitio/test/splitio_test.dart @@ -101,4 +101,26 @@ void main() { expect(_platform.methodArguments, {'splitName': 'my_split'}); }); }); + + group('userConsent', () { + test('get user consent', () async { + var splitio = Splitio('api-key', 'matching-key'); + splitio.getUserConsent(); + + expect(_platform.methodName, 'getUserConsent'); + }); + + test('set user consent', () async { + var splitio = Splitio('api-key', 'matching-key'); + splitio.setUserConsent(true); + + expect(_platform.methodName, 'setUserConsent'); + expect(_platform.methodArguments, { + 'matchingKey': 'matching-key', + 'apiKey': 'api-key', + 'sdkConfiguration': {}, + 'value': true, + }); + }); + }); } diff --git a/splitio_android/pubspec.yaml b/splitio_android/pubspec.yaml index 33d267c..33684f1 100644 --- a/splitio_android/pubspec.yaml +++ b/splitio_android/pubspec.yaml @@ -19,7 +19,9 @@ flutter: dependencies: flutter: sdk: flutter - splitio_platform_interface: ^1.1.0 +# splitio_platform_interface: ^1.1.0 + splitio_platform_interface: + path: ../splitio_platform_interface dev_dependencies: flutter_test: diff --git a/splitio_ios/example/ios/SplitTests/SplitMethodParserTests.swift b/splitio_ios/example/ios/SplitTests/SplitMethodParserTests.swift index 12fa488..e2d96a2 100644 --- a/splitio_ios/example/ios/SplitTests/SplitMethodParserTests.swift +++ b/splitio_ios/example/ios/SplitTests/SplitMethodParserTests.swift @@ -297,6 +297,28 @@ class SplitMethodParserTests: XCTestCase { XCTAssert(providerHelper.splitClientConfigValue?.impressionListener != nil) XCTAssert(providerHelper.splitClientConfigValue?.streamingEnabled == false) } + + func testGetUserConsent() { + methodParser?.onMethodCall(methodName: "getUserConsent", arguments: [], result: { (_: Any?) in }) + + guard let wrapper = splitWrapper as? SplitWrapperStub else { + XCTFail() + return + } + + XCTAssert(wrapper.userConsent == "unknown") + } + + func testSetUserConsent() { + methodParser?.onMethodCall(methodName: "setUserConsent", arguments: [], result: { (_: Any?) in }) + + guard let wrapper = splitWrapper as? SplitWrapperStub else { + XCTFail() + return + } + + XCTAssert(wrapper.userConsent == "declined") + } } class SplitWrapperStub: SplitWrapper { @@ -316,6 +338,7 @@ class SplitWrapperStub: SplitWrapper { var attributeNameValue: String = "" var splitsCalled = false var splitNamesCalled = false + var userConsent = "unknown" func getClient(matchingKey: String, bucketingKey: String?) -> SplitClient? { matchingKeyValue = matchingKey @@ -440,6 +463,18 @@ class SplitWrapperStub: SplitWrapper { splitNameValue = splitName return nil } + + func getUserConsent() -> String { + return userConsent + } + + func setUserConsent(enabled: Bool) { + if (enabled) { + userConsent = "granted" + } else { + userConsent = "declined" + } + } } class SplitProviderHelperStub: SplitProviderHelper { diff --git a/splitio_ios/example/ios/SplitTests/SplitTests.swift b/splitio_ios/example/ios/SplitTests/SplitTests.swift index 7853301..e4c02ad 100644 --- a/splitio_ios/example/ios/SplitTests/SplitTests.swift +++ b/splitio_ios/example/ios/SplitTests/SplitTests.swift @@ -181,6 +181,26 @@ class SplitTests: XCTestCase { let split = splitWrapper.split(splitName: "my-split") XCTAssert(manager.splitNameValue == "my-split") } + + func testGetUserConsent() { + let manager = SplitManagerStub() + let factoryProvider = SplitFactoryProviderStub(manager: manager) + splitWrapper = DefaultSplitWrapper(splitFactoryProvider: factoryProvider) + let userConsent = splitWrapper.getUserConsent() + XCTAssert(userConsent == "unknown") + } + + func testSetUserConsent() { + let manager = SplitManagerStub() + let factoryProvider = SplitFactoryProviderStub(manager: manager) + splitWrapper = DefaultSplitWrapper(splitFactoryProvider: factoryProvider) + splitWrapper.setUserConsent(enabled: true) + let grantedUserConsent = splitWrapper.getUserConsent() + splitWrapper.setUserConsent(enabled: false) + let declinedUserConsent = splitWrapper.getUserConsent() + XCTAssert(grantedUserConsent == "granted") + XCTAssert(declinedUserConsent == "declined") + } } class SplitFactoryProviderStub: SplitFactoryProvider { diff --git a/splitio_ios/ios/Classes/Constants.swift b/splitio_ios/ios/Classes/Constants.swift index c5e6cce..bea9d65 100644 --- a/splitio_ios/ios/Classes/Constants.swift +++ b/splitio_ios/ios/Classes/Constants.swift @@ -24,6 +24,8 @@ enum Method: String { case splits = "splits" case split = "split" case impressionLog = "impressionLog" + case getUserConsent = "getUserConsent" + case setUserConsent = "setUserConsent" } enum Argument: String { diff --git a/splitio_ios/ios/Classes/SplitMethodParser.swift b/splitio_ios/ios/Classes/SplitMethodParser.swift index d4c6aba..6c8a216 100644 --- a/splitio_ios/ios/Classes/SplitMethodParser.swift +++ b/splitio_ios/ios/Classes/SplitMethodParser.swift @@ -133,6 +133,12 @@ class DefaultSplitMethodParser: SplitMethodParser { case .split: result(SplitView.asMap(splitView: splitWrapper?.split(splitName: argumentParser.getStringArgument(argumentName: .splitName, arguments: arguments) ?? ""))) break + case .getUserConsent: + result(splitWrapper?.getUserConsent()) + break + case .setUserConsent: + splitWrapper?.setUserConsent(enabled: argumentParser.getBooleanArgument(argumentName: .value, arguments: arguments)) + result(nil) default: result(FlutterMethodNotImplemented) break diff --git a/splitio_ios/ios/Classes/SplitWrapper.swift b/splitio_ios/ios/Classes/SplitWrapper.swift index f9b65d9..69e764f 100644 --- a/splitio_ios/ios/Classes/SplitWrapper.swift +++ b/splitio_ios/ios/Classes/SplitWrapper.swift @@ -16,6 +16,10 @@ protocol SplitWrapper: EvaluationWrapper, AttributesWrapper { func splits() -> [SplitView] func split(splitName: String) -> SplitView? + + func getUserConsent() -> String + + func setUserConsent(enabled: Bool) } protocol EvaluationWrapper { @@ -227,4 +231,26 @@ class DefaultSplitWrapper: SplitWrapper { return nil } } + + func getUserConsent() -> String { + if let splitFactory = splitFactory { + let userConsent: UserConsent = splitFactory.userConsent + + if (userConsent == .granted) { + return "granted" + } else if (userConsent == .declined) { + return "declined" + } else { + return "unknown" + } + } else { + return "unknown" + } + } + + func setUserConsent(enabled: Bool) { + if let splitFactory = splitFactory { + splitFactory.setUserConsent(enabled: enabled) + } + } } diff --git a/splitio_ios/pubspec.yaml b/splitio_ios/pubspec.yaml index 4481a13..a2dd2b9 100644 --- a/splitio_ios/pubspec.yaml +++ b/splitio_ios/pubspec.yaml @@ -18,7 +18,9 @@ flutter: dependencies: flutter: sdk: flutter - splitio_platform_interface: ^1.1.0 +# splitio_platform_interface: ^1.1.0 + splitio_platform_interface: + path: ../splitio_platform_interface dev_dependencies: flutter_test: diff --git a/splitio_platform_interface/lib/method_channel_platform.dart b/splitio_platform_interface/lib/method_channel_platform.dart index b499305..8132d28 100644 --- a/splitio_platform_interface/lib/method_channel_platform.dart +++ b/splitio_platform_interface/lib/method_channel_platform.dart @@ -324,6 +324,24 @@ class MethodChannelPlatform extends SplitioPlatform { return _impressionsMethodCallHandler.stream(); } + @override + Future getUserConsent() async { + String invokeMethod = + (await _methodChannel.invokeMethod('getUserConsent')) as String; + if (invokeMethod == 'granted') { + return UserConsent.granted; + } else if (invokeMethod == 'declined') { + return UserConsent.declined; + } else { + return UserConsent.unknown; + } + } + + @override + Future setUserConsent(bool enabled) async { + await _methodChannel.invokeMethod('setUserConsent', {'value': enabled}); + } + String _buildMapKey(String matchingKey, String? bucketingKey) { return '${matchingKey}_$bucketingKey'; } diff --git a/splitio_platform_interface/lib/splitio_platform_interface.dart b/splitio_platform_interface/lib/splitio_platform_interface.dart index 729e001..3e71adb 100644 --- a/splitio_platform_interface/lib/splitio_platform_interface.dart +++ b/splitio_platform_interface/lib/splitio_platform_interface.dart @@ -47,6 +47,14 @@ abstract class _FactoryPlatform { Stream impressionsStream() { throw UnimplementedError(); } + + Future getUserConsent() { + throw UnimplementedError(); + } + + Future setUserConsent(bool enabled) { + throw UnimplementedError(); + } } abstract class _ClientPlatform { diff --git a/splitio_platform_interface/test/method_channel_platform_test.dart b/splitio_platform_interface/test/method_channel_platform_test.dart index 72cb4ed..21ed1e2 100644 --- a/splitio_platform_interface/test/method_channel_platform_test.dart +++ b/splitio_platform_interface/test/method_channel_platform_test.dart @@ -54,6 +54,8 @@ void main() { case 'removeAttribute': case 'clearAttributes': return true; + case 'getUserConsent': + return 'declined'; } return null; }); @@ -372,8 +374,8 @@ void main() { apiKey: 'api-key', matchingKey: 'matching-key', bucketingKey: 'bucketing-key', - sdkConfiguration: - SplitConfiguration(logLevel: SplitLogLevel.debug, streamingEnabled: false)); + sdkConfiguration: SplitConfiguration( + logLevel: SplitLogLevel.debug, streamingEnabled: false)); expect(methodName, 'init'); expect(methodArguments, { 'apiKey': 'api-key', @@ -514,4 +516,27 @@ void main() { 'attributes': {} }); }); + + group('userConsent', () { + test('get user consent', () async { + UserConsent userConsent = await _platform.getUserConsent(); + + expect(methodName, 'getUserConsent'); + expect(userConsent, UserConsent.declined); + }); + + test('set user consent enabled', () { + _platform.setUserConsent(true); + + expect(methodName, 'setUserConsent'); + expect(methodArguments, {'value': true}); + }); + + test('set user consent disabled', () { + _platform.setUserConsent(false); + + expect(methodName, 'setUserConsent'); + expect(methodArguments, {'value': false}); + }); + }); }