Skip to content

Commit

Permalink
[3.x] Remove Kount (#742)
Browse files Browse the repository at this point in the history
* Remove kount from gradle dependencies.

* Remove kount data collector jar file.

* Fix DataCollectorUnitTest.

* Update DataCollector test.

* Fix broken configuration kount parsing test.

* Update CHANGELOG.
  • Loading branch information
sshropshire authored Jun 8, 2023
1 parent c738c6b commit cb1f33e
Show file tree
Hide file tree
Showing 9 changed files with 33 additions and 303 deletions.
Original file line number Diff line number Diff line change
@@ -1,15 +1,12 @@
package com.braintreepayments.api;

import android.text.TextUtils;

import androidx.appcompat.app.AppCompatActivity;
import androidx.test.internal.runner.junit4.AndroidJUnit4ClassRunner;

import com.braintreepayments.api.interfaces.BraintreeResponseListener;
import com.braintreepayments.api.test.BraintreeActivityTestRule;
import com.braintreepayments.api.test.TestActivity;
import com.braintreepayments.testutils.TestConfigurationBuilder;
import com.braintreepayments.testutils.TestConfigurationBuilder.TestKountConfigurationBuilder;

import org.json.JSONException;
import org.json.JSONObject;
Expand All @@ -21,8 +18,6 @@
import java.util.concurrent.CountDownLatch;

import static com.braintreepayments.api.BraintreeFragmentTestUtils.getFragmentWithConfiguration;
import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertFalse;
import static junit.framework.Assert.assertNotNull;
import static junit.framework.Assert.assertNull;
import static junit.framework.Assert.fail;
Expand All @@ -44,61 +39,7 @@ public void setup() {
}

@Test(timeout = 10000)
public void collectDeviceData_withListener() throws InterruptedException {
String configuration = new TestConfigurationBuilder()
.kount(new TestKountConfigurationBuilder()
.kountMerchantId("500000"))
.build();
BraintreeFragment fragment = getFragmentWithConfiguration(mActivity, configuration);

DataCollector.collectDeviceData(fragment, new BraintreeResponseListener<String>() {
@Override
public void onResponse(String deviceData) {
try {
JSONObject json = new JSONObject(deviceData);
assertFalse(TextUtils.isEmpty(json.getString("device_session_id")));
assertEquals("500000", json.getString("fraud_merchant_id"));
assertNotNull(json.getString("correlation_id"));
} catch (JSONException e) {
fail(e.getMessage());
}

mCountDownLatch.countDown();
}
});

mCountDownLatch.await();
}

@Test(timeout = 10000)
public void collectDeviceData_withListener_usesDirectMerchantId() throws InterruptedException {
String configuration = new TestConfigurationBuilder()
.kount(new TestKountConfigurationBuilder()
.kountMerchantId("600000"))
.build();
BraintreeFragment fragment = getFragmentWithConfiguration(mActivity, configuration);

DataCollector.collectDeviceData(fragment, "600001", new BraintreeResponseListener<String>() {
@Override
public void onResponse(String deviceData) {
try {
JSONObject json = new JSONObject(deviceData);
assertFalse(TextUtils.isEmpty(json.getString("device_session_id")));
assertEquals("600001", json.getString("fraud_merchant_id"));
assertNotNull(json.getString("correlation_id"));
} catch (JSONException e) {
fail(e.getMessage());
}

mCountDownLatch.countDown();
}
});

mCountDownLatch.await();
}

@Test(timeout = 10000)
public void collectDeviceData_doesNotCollectKountDataIfKountDisabledInConfiguration() throws InterruptedException {
public void collectDeviceData_returnsCorrelationIdAndDoesNotCollectKountData() throws InterruptedException {
BraintreeFragment fragment = getFragmentWithConfiguration(mActivity, new TestConfigurationBuilder().build());

DataCollector.collectDeviceData(fragment, new BraintreeResponseListener<String>() {
Expand Down
107 changes: 18 additions & 89 deletions Braintree/src/main/java/com/braintreepayments/api/DataCollector.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,9 @@
import android.text.TextUtils;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.annotation.VisibleForTesting;

import com.braintreepayments.api.interfaces.BraintreeResponseListener;
import com.braintreepayments.api.interfaces.ConfigurationListener;
import com.braintreepayments.api.internal.UUIDHelper;
import com.braintreepayments.api.models.ClientToken;
import com.braintreepayments.api.models.Configuration;
import com.braintreepayments.api.models.PaymentMethodNonce;
Expand Down Expand Up @@ -44,18 +41,19 @@ public static void collectDeviceData(BraintreeFragment fragment, BraintreeRespon

/**
* Collects device data based on your merchant configuration.
*
* <p>
* We recommend that you call this method as early as possible, e.g. at app launch. If that's too early,
* call it at the beginning of customer checkout.
*
* <p>
* Use the return value on your server, e.g. with `Transaction.sale`.
*
* @param fragment {@link BraintreeFragment}
* @param fragment {@link BraintreeFragment}
* @param merchantId Optional - Custom Kount merchant id. Leave blank to use the default.
* @param listener listener called with the deviceData string that should be passed into server-side calls, such as `Transaction.sale`.
* @param listener listener called with the deviceData string that should be passed into server-side calls, such as `Transaction.sale`.
* @deprecated
*/
public static void collectDeviceData(final BraintreeFragment fragment, final String merchantId,
final BraintreeResponseListener<String> listener) {
@Deprecated
public static void collectDeviceData(final BraintreeFragment fragment, final String merchantId, final BraintreeResponseListener<String> listener) {
fragment.waitForConfiguration(new ConfigurationListener() {
@Override
public void onConfigurationFetched(Configuration configuration) {
Expand All @@ -66,35 +64,10 @@ public void onConfigurationFetched(Configuration configuration) {
if (!TextUtils.isEmpty(clientMetadataId)) {
deviceData.put(CORRELATION_ID_KEY, clientMetadataId);
}
} catch (JSONException ignored) {}

if (configuration.getKount().isEnabled()) {
final String id;
if (merchantId != null) {
id = merchantId;
} else {
id = configuration.getKount().getKountMerchantId();
}

try {
final String deviceSessionId = UUIDHelper.getFormattedUUID();
startDeviceCollector(fragment, id, deviceSessionId, new BraintreeResponseListener<String>() {
@Override
public void onResponse(String sessionId) {
try {
deviceData.put(DEVICE_SESSION_ID_KEY, deviceSessionId);
deviceData.put(FRAUD_MERCHANT_ID_KEY, id);
} catch (JSONException ignored) {}

listener.onResponse(deviceData.toString());
}
});
} catch (ClassNotFoundException | NoClassDefFoundError | NumberFormatException ignored) {
listener.onResponse(deviceData.toString());
}
} else {
listener.onResponse(deviceData.toString());
} catch (JSONException ignored) {
}

listener.onResponse(deviceData.toString());
}
});
}
Expand All @@ -113,7 +86,8 @@ public static void collectPayPalDeviceData(final BraintreeFragment fragment, fin
if (!TextUtils.isEmpty(clientMetadataId)) {
deviceData.put(CORRELATION_ID_KEY, clientMetadataId);
}
} catch (JSONException ignored) {}
} catch (JSONException ignored) {
}

listener.onResponse(deviceData.toString());
}
Expand All @@ -127,66 +101,29 @@ public static void collectPayPalDeviceData(final BraintreeFragment fragment, fin
public static String getPayPalClientMetadataId(Context context) {
try {
return PayPalOneTouchCore.getClientMetadataId(context);
} catch (NoClassDefFoundError ignored) {}
} catch (NoClassDefFoundError ignored) {
}

try {
return PayPalDataCollector.getClientMetadataId(context);
} catch (NoClassDefFoundError ignored) {}
} catch (NoClassDefFoundError ignored) {
}

return "";
}

private static void startDeviceCollector(final BraintreeFragment fragment, final String merchantId,
final String deviceSessionId, @Nullable final BraintreeResponseListener<String> listener)
throws ClassNotFoundException, NumberFormatException {
fragment.sendAnalyticsEvent("data-collector.kount.started");

Class.forName(com.kount.api.DataCollector.class.getName());

fragment.waitForConfiguration(new ConfigurationListener() {
@Override
public void onConfigurationFetched(Configuration configuration) {
final com.kount.api.DataCollector dataCollector = com.kount.api.DataCollector.getInstance();
dataCollector.setContext(fragment.getApplicationContext());
dataCollector.setMerchantID(Integer.parseInt(merchantId));
dataCollector.setLocationCollectorConfig(com.kount.api.DataCollector.LocationConfig.COLLECT);
dataCollector.setEnvironment(getDeviceCollectorEnvironment(configuration.getEnvironment()));

dataCollector.collectForSession(deviceSessionId, new com.kount.api.DataCollector.CompletionHandler() {
@Override
public void completed(String sessionID) {
fragment.sendAnalyticsEvent("data-collector.kount.succeeded");

if (listener != null) {
listener.onResponse(sessionID);
}
}

@Override
public void failed(String sessionID, final com.kount.api.DataCollector.Error error) {
fragment.sendAnalyticsEvent("data-collector.kount.failed");

if (listener != null) {
listener.onResponse(sessionID);
}
}
});
}
});
}

static void collectRiskData(final BraintreeFragment fragment,
@NonNull final PaymentMethodNonce paymentMethodNonce) {
fragment.waitForConfiguration(new ConfigurationListener() {
@Override
public void onConfigurationFetched(Configuration configuration) {
if (configuration.getCardConfiguration().isFraudDataCollectionEnabled()) {
HashMap<String,String> additionalProperties = new HashMap<>();
HashMap<String, String> additionalProperties = new HashMap<>();
additionalProperties.put("rda_tenant", "bt_card");
additionalProperties.put("mid", configuration.getMerchantId());

if (fragment.getAuthorization() instanceof ClientToken) {
String customerId = ((ClientToken)fragment.getAuthorization()).getCustomerId();
String customerId = ((ClientToken) fragment.getAuthorization()).getCustomerId();
if (customerId != null) {
additionalProperties.put("cid", customerId);
}
Expand All @@ -203,12 +140,4 @@ public void onConfigurationFetched(Configuration configuration) {
}
});
}

@VisibleForTesting
static int getDeviceCollectorEnvironment(String environment) {
if ("production".equalsIgnoreCase(environment)) {
return com.kount.api.DataCollector.ENVIRONMENT_PRODUCTION;
}
return com.kount.api.DataCollector.ENVIRONMENT_TEST;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@ public class Configuration {
private static final String BRAINTREE_API_KEY = "braintreeApi";
private static final String PAYPAL_ENABLED_KEY = "paypalEnabled";
private static final String PAYPAL_KEY = "paypal";
private static final String KOUNT_KEY = "kount";
private static final String GOOGLE_PAYMENT_KEY = "androidPay";
private static final String THREE_D_SECURE_ENABLED_KEY = "threeDSecureEnabled";
private static final String PAY_WITH_VENMO_KEY = "payWithVenmo";
Expand Down Expand Up @@ -92,7 +91,8 @@ protected Configuration(@Nullable String configurationString) throws JSONExcepti
mGooglePaymentConfiguration = GooglePaymentConfiguration.fromJson(json.optJSONObject(GOOGLE_PAYMENT_KEY));
mThreeDSecureEnabled = json.optBoolean(THREE_D_SECURE_ENABLED_KEY, false);
mVenmoConfiguration = VenmoConfiguration.fromJson(json.optJSONObject(PAY_WITH_VENMO_KEY));
mKountConfiguration = KountConfiguration.fromJson(json.optJSONObject(KOUNT_KEY));
// kount is always disabled
mKountConfiguration = KountConfiguration.fromJson(null);
mUnionPayConfiguration = UnionPayConfiguration.fromJson(json.optJSONObject(UNIONPAY_KEY));
mVisaCheckoutConfiguration = VisaCheckoutConfiguration.fromJson(json.optJSONObject(VISA_CHECKOUT_KEY));
mGraphQLConfiguration = GraphQLConfiguration.fromJson(json.optJSONObject(GRAPHQL_KEY));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -116,13 +116,6 @@ public TestConfigurationBuilder payWithVenmo(TestVenmoConfigurationBuilder venmo
return this;
}

public TestConfigurationBuilder kount(TestKountConfigurationBuilder kountConfigurationBuilder) {
try {
put(new JSONObject(kountConfigurationBuilder.build()));
} catch (JSONException ignored) {}
return this;
}

public TestConfigurationBuilder visaCheckout(TestVisaCheckoutConfigurationBuilder visaCheckoutConfigurationBuilder) {
try {
put(new JSONObject(visaCheckoutConfigurationBuilder.build()));
Expand Down Expand Up @@ -196,13 +189,6 @@ public TestPayPalConfigurationBuilder paypal() {
return new TestPayPalConfigurationBuilder(true);
}

public TestKountConfigurationBuilder kount() {
try {
return new TestKountConfigurationBuilder(mJsonBody.getJSONObject("kount"));
} catch (JSONException ignored) {}
return new TestKountConfigurationBuilder();
}

public TestVisaCheckoutConfigurationBuilder visaCheckout() {
try {
return new TestVisaCheckoutConfigurationBuilder(mJsonBody.getJSONObject("visaCheckout"));
Expand Down Expand Up @@ -355,22 +341,6 @@ public TestGooglePaymentConfigurationBuilder paypalClientId(String paypalClientI
}
}

public static class TestKountConfigurationBuilder extends JSONBuilder {

public TestKountConfigurationBuilder() {
super();
}

protected TestKountConfigurationBuilder(JSONObject json) {
super(json);
}

public TestKountConfigurationBuilder kountMerchantId(String kountMerchantid) {
put(kountMerchantid);
return this;
}
}

public static class TestVisaCheckoutConfigurationBuilder extends JSONBuilder {

public TestVisaCheckoutConfigurationBuilder() {
Expand Down
Loading

0 comments on commit cb1f33e

Please sign in to comment.