diff --git a/CHANGELOG.md b/CHANGELOG.md index 69bb5701..0bace614 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -14,6 +14,13 @@ CHANGELOG `FactorsResponse.getSubscores()` method. Use `getRiskScoreReasons()` instead. * BREAKING: Java 17 is now required (previously Java 11). +* Added `CREDIT_APPLICATION` and `FUND_TRANSFER` to the `Event.Type` enum. +* Added the input `/event/party`. This is the party submitting the + transaction. You may provide this using the `party` method on + `Event.Builder`. +* Added the input `/payment/method`. This is the payment method associated + with the transaction. You may provide this using the `method` method on + `Payment.Builder`. 3.9.0 ------------------ diff --git a/README.md b/README.md index cf298208..7684ec97 100644 --- a/README.md +++ b/README.md @@ -179,6 +179,7 @@ Transaction request = new Transaction.Builder( .build() ).event( new Event.Builder() + .party(Event.Party.CUSTOMER) .shopId("2432") .time(new Date()) .transactionId("tr1242") @@ -196,6 +197,7 @@ Transaction request = new Transaction.Builder( ).payment( new Payment.Builder() .declineCode("invalid") + .method(Payment.Method.CARD) .processor(Payment.Processor.ADYEN) .wasAuthorized(false) .build() diff --git a/src/main/java/com/maxmind/minfraud/request/Event.java b/src/main/java/com/maxmind/minfraud/request/Event.java index d49d8304..1ca0da1a 100644 --- a/src/main/java/com/maxmind/minfraud/request/Event.java +++ b/src/main/java/com/maxmind/minfraud/request/Event.java @@ -12,12 +12,14 @@ */ public final class Event extends AbstractModel { + private final Party party; private final String transactionId; private final String shopId; private final ZonedDateTime time; private final Type type; private Event(Event.Builder builder) { + party = builder.party; transactionId = builder.transactionId; shopId = builder.shopId; time = builder.time; @@ -28,11 +30,21 @@ private Event(Event.Builder builder) { * {@code Builder} creates instances of {@code Event} from values set by the builder's methods. */ public static final class Builder { + Party party; String transactionId; String shopId; ZonedDateTime time; Type type; + /** + * @param party The party submitting the transaction. + * @return The builder object. + */ + public Event.Builder party(Party party) { + this.party = party; + return this; + } + /** * @param id Your internal ID for the transaction. We can use this to locate a specific * transaction in our logs, and it will also show up in email alerts and @@ -90,6 +102,14 @@ public Event build() { } } + /** + * @return The party submitting the transaction. + */ + @JsonProperty("party") + public Party getParty() { + return party; + } + /** * @return The transaction ID. */ @@ -142,10 +162,18 @@ public enum Type { * The account was logged into */ ACCOUNT_LOGIN, + /** + * A credit application was submitted + */ + CREDIT_APPLICATION, /** * The account email was changed */ EMAIL_CHANGE, + /** + * A fund transfer was initiated + */ + FUND_TRANSFER, /** * The account password was reset */ @@ -178,4 +206,25 @@ public String toString() { return this.name().toLowerCase(); } } + + /** + * The enumerated event party types. + */ + public enum Party { + /** + * An agent is submitting the transaction + */ + AGENT, + /** + * A customer is submitting the transaction + */ + CUSTOMER; + + /** + * @return a string representation of the object. + */ + public String toString() { + return this.name().toLowerCase(); + } + } } \ No newline at end of file diff --git a/src/main/java/com/maxmind/minfraud/request/Payment.java b/src/main/java/com/maxmind/minfraud/request/Payment.java index 40d0937b..47ac7f26 100644 --- a/src/main/java/com/maxmind/minfraud/request/Payment.java +++ b/src/main/java/com/maxmind/minfraud/request/Payment.java @@ -7,11 +7,13 @@ * The payment information for the transaction. */ public final class Payment extends AbstractModel { + private final Method method; private final Processor processor; private final Boolean wasAuthorized; private final String declineCode; private Payment(Payment.Builder builder) { + method = builder.method; processor = builder.processor; wasAuthorized = builder.wasAuthorized; declineCode = builder.declineCode; @@ -22,10 +24,20 @@ private Payment(Payment.Builder builder) { * methods. */ public static final class Builder { + Method method; Processor processor; Boolean wasAuthorized; String declineCode; + /** + * @param method The payment method used for the transaction. + * @return The builder object. + */ + public Payment.Builder method(Method method) { + this.method = method; + return this; + } + /** * @param processor The payment processor used for the transaction. * @return The builder object. @@ -64,6 +76,14 @@ public Payment build() { } } + /** + * @return The payment method. + */ + @JsonProperty("method") + public Method getMethod() { + return method; + } + /** * @return The payment processor. */ @@ -262,4 +282,57 @@ public String toString() { return this.name().toLowerCase(); } } + + /** + * Enumeration of payment methods + */ + public enum Method { + /** + * Bank debit payment + */ + BANK_DEBIT, + /** + * Bank redirect payment + */ + BANK_REDIRECT, + /** + * Bank transfer payment + */ + BANK_TRANSFER, + /** + * Buy now, pay later payment + */ + BUY_NOW_PAY_LATER, + /** + * Card payment + */ + CARD, + /** + * Cryptocurrency payment + */ + CRYPTO, + /** + * Digital wallet payment + */ + DIGITAL_WALLET, + /** + * Gift card payment + */ + GIFT_CARD, + /** + * Real time payment + */ + REAL_TIME_PAYMENT, + /** + * Rewards payment + */ + REWARDS; + + /** + * @return a string representation of the object. + */ + public String toString() { + return this.name().toLowerCase(); + } + } } diff --git a/src/test/java/com/maxmind/minfraud/request/EventTest.java b/src/test/java/com/maxmind/minfraud/request/EventTest.java index c91b1b5d..bbcdf77b 100644 --- a/src/test/java/com/maxmind/minfraud/request/EventTest.java +++ b/src/test/java/com/maxmind/minfraud/request/EventTest.java @@ -3,6 +3,7 @@ import static org.junit.jupiter.api.Assertions.assertEquals; import com.maxmind.minfraud.request.Event.Builder; +import com.maxmind.minfraud.request.Event.Party; import com.maxmind.minfraud.request.Event.Type; import java.time.ZonedDateTime; import java.util.Date; @@ -10,6 +11,15 @@ public class EventTest { + @Test + public void testParty() { + Event event = new Builder().party(Party.AGENT).build(); + assertEquals(Party.AGENT, event.getParty()); + + event = new Builder().party(Party.CUSTOMER).build(); + assertEquals(Party.CUSTOMER, event.getParty()); + } + @Test public void testTransactionId() { Event event = new Builder().transactionId("t12").build(); @@ -43,5 +53,11 @@ public void testType() { event = new Builder().type(Type.PAYOUT_CHANGE).build(); assertEquals(Type.PAYOUT_CHANGE, event.getType()); + + event = new Builder().type(Type.CREDIT_APPLICATION).build(); + assertEquals(Type.CREDIT_APPLICATION, event.getType()); + + event = new Builder().type(Type.FUND_TRANSFER).build(); + assertEquals(Type.FUND_TRANSFER, event.getType()); } } diff --git a/src/test/java/com/maxmind/minfraud/request/PaymentTest.java b/src/test/java/com/maxmind/minfraud/request/PaymentTest.java index 171fc1f6..d2367972 100644 --- a/src/test/java/com/maxmind/minfraud/request/PaymentTest.java +++ b/src/test/java/com/maxmind/minfraud/request/PaymentTest.java @@ -4,11 +4,24 @@ import static org.junit.jupiter.api.Assertions.assertTrue; import com.maxmind.minfraud.request.Payment.Builder; +import com.maxmind.minfraud.request.Payment.Method; import com.maxmind.minfraud.request.Payment.Processor; import org.junit.jupiter.api.Test; public class PaymentTest { + @Test + public void testMethod() { + Payment payment = new Builder().method(Method.CARD).build(); + assertEquals(Method.CARD, payment.getMethod()); + + payment = new Builder().method(Method.DIGITAL_WALLET).build(); + assertEquals(Method.DIGITAL_WALLET, payment.getMethod()); + + payment = new Builder().method(Method.BUY_NOW_PAY_LATER).build(); + assertEquals(Method.BUY_NOW_PAY_LATER, payment.getMethod()); + } + @Test public void testProcessor() { Payment payment = new Builder().processor(Processor.ADYEN).build(); diff --git a/src/test/java/com/maxmind/minfraud/request/RequestTestHelper.java b/src/test/java/com/maxmind/minfraud/request/RequestTestHelper.java index 6ee72e6f..6319ec8e 100644 --- a/src/test/java/com/maxmind/minfraud/request/RequestTestHelper.java +++ b/src/test/java/com/maxmind/minfraud/request/RequestTestHelper.java @@ -58,6 +58,7 @@ private static Transaction makeTransaction(Email e) throws Exception { .event( new Event .Builder() + .party(Event.Party.CUSTOMER) .transactionId("txn3134133") .shopId("s2123") .time(ZonedDateTime.parse("2012-04-12T23:20:50.52Z")) @@ -102,6 +103,7 @@ private static Transaction makeTransaction(Email e) throws Exception { .build() ).payment( new Payment.Builder() + .method(Payment.Method.CARD) .processor(Payment.Processor.STRIPE) .wasAuthorized(false) .declineCode("invalid number") diff --git a/src/test/resources/test-data/full-request-email-md5.json b/src/test/resources/test-data/full-request-email-md5.json index 670fd607..eaa7b5d8 100644 --- a/src/test/resources/test-data/full-request-email-md5.json +++ b/src/test/resources/test-data/full-request-email-md5.json @@ -1,5 +1,6 @@ { "event": { + "party": "customer", "transaction_id": "txn3134133", "shop_id": "s2123", "time": "2012-04-12T23:20:50.52Z", @@ -41,6 +42,7 @@ "delivery_speed": "same_day" }, "payment": { + "method": "card", "processor": "stripe", "was_authorized": false, "decline_code": "invalid number" diff --git a/src/test/resources/test-data/full-request.json b/src/test/resources/test-data/full-request.json index 98085be6..a2a70cce 100644 --- a/src/test/resources/test-data/full-request.json +++ b/src/test/resources/test-data/full-request.json @@ -1,5 +1,6 @@ { "event": { + "party": "customer", "transaction_id": "txn3134133", "shop_id": "s2123", "time": "2012-04-12T23:20:50.52Z", @@ -41,6 +42,7 @@ "delivery_speed": "same_day" }, "payment": { + "method": "card", "processor": "stripe", "was_authorized": false, "decline_code": "invalid number"