Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.ibanity.apis.client.products.isabel_connect.models;

import lombok.AccessLevel;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.NoArgsConstructor;
import lombok.ToString;
import lombok.experimental.SuperBuilder;

@Data
@ToString(callSuper = true)
@EqualsAndHashCode(callSuper = true)
@SuperBuilder(toBuilder = true)
@NoArgsConstructor
@AllArgsConstructor(access = AccessLevel.PRIVATE)
public class PaymentNotification extends IsabelModel<String> {
public static final String RESOURCE_TYPE = "paymentNotification";

private String notificationType;
private String createdAt;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.ibanity.apis.client.products.isabel_connect.models.delete;

import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.ToString;

import java.util.Map;

import static java.util.Collections.emptyMap;

@Getter
@Builder
@ToString
@EqualsAndHashCode
public class PaymentNotificationDeleteQuery {
private String accessToken;
private String paymentNotificationId;

@Builder.Default
private Map<String, String> additionalHeaders = emptyMap();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.ibanity.apis.client.products.isabel_connect.models.read;

import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.ToString;

import java.util.Map;

import static java.util.Collections.emptyMap;

@Getter
@Builder
@ToString
@EqualsAndHashCode
public class PaymentNotificationsReadQuery {
private String accessToken;
private IsabelPagingSpec pagingSpec;

@Builder.Default
private Map<String, String> additionalHeaders = emptyMap();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package com.ibanity.apis.client.products.isabel_connect.models.read;

import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.ToString;

import java.util.Map;

import static java.util.Collections.emptyMap;

@Getter
@Builder
@ToString
@EqualsAndHashCode
public class PaymentStatusReadQuery {
private String accessToken;
private String bulkPaymentInitiationRequestId;
private String notificationId;

@Builder.Default
private Map<String, String> additionalHeaders = emptyMap();
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,4 +15,8 @@ public interface IsabelConnectService {
TransactionService transactionService();

TokenService tokenService();

PaymentNotificationService paymentNotificationService();

PaymentStatusService paymentStatusService();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package com.ibanity.apis.client.products.isabel_connect.services;

import com.ibanity.apis.client.models.IsabelCollection;
import com.ibanity.apis.client.products.isabel_connect.models.PaymentNotification;
import com.ibanity.apis.client.products.isabel_connect.models.delete.PaymentNotificationDeleteQuery;
import com.ibanity.apis.client.products.isabel_connect.models.read.PaymentNotificationsReadQuery;

public interface PaymentNotificationService {
IsabelCollection<PaymentNotification> list(PaymentNotificationsReadQuery query);
void delete(PaymentNotificationDeleteQuery query);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package com.ibanity.apis.client.products.isabel_connect.services;

import com.ibanity.apis.client.products.isabel_connect.models.read.PaymentStatusReadQuery;

public interface PaymentStatusService {
String find(PaymentStatusReadQuery query);
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@ public class IsabelConnectServiceImpl implements IsabelConnectService {
private final IntradayTransactionService intradayTransactionService;
private final TransactionService transactionService;
private final TokenService tokenService;
private final PaymentNotificationService paymentNotificationService;
private final PaymentStatusService paymentStatusService;

public IsabelConnectServiceImpl(
ApiUrlProvider apiUrlProvider,
Expand All @@ -26,6 +28,8 @@ public IsabelConnectServiceImpl(
transactionService = new TransactionServiceImpl(apiUrlProvider, ibanityHttpClient);
tokenService = new TokenServiceImpl(apiUrlProvider, oAuthHttpClient);
bulkPaymentInitiationRequestService = new BulkPaymentInitiationRequestServiceImpl(apiUrlProvider, new IbanityResponseHandler(), ibanityHttpClient);
paymentNotificationService = new PaymentNotificationServiceImpl(apiUrlProvider, ibanityHttpClient);
paymentStatusService = new PaymentStatusServiceImpl(apiUrlProvider, ibanityHttpClient);
}

@Override
Expand All @@ -48,4 +52,10 @@ public IsabelConnectServiceImpl(

@Override
public TokenService tokenService() { return tokenService; }

@Override
public PaymentNotificationService paymentNotificationService() { return paymentNotificationService; }

@Override
public PaymentStatusService paymentStatusService() { return paymentStatusService; }
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
package com.ibanity.apis.client.products.isabel_connect.services.impl;

import com.ibanity.apis.client.http.IbanityHttpClient;
import com.ibanity.apis.client.mappers.IsabelModelMapper;
import com.ibanity.apis.client.models.IbanityProduct;
import com.ibanity.apis.client.models.IsabelCollection;
import com.ibanity.apis.client.products.isabel_connect.models.PaymentNotification;
import com.ibanity.apis.client.products.isabel_connect.models.delete.PaymentNotificationDeleteQuery;
import com.ibanity.apis.client.products.isabel_connect.models.read.PaymentNotificationsReadQuery;
import com.ibanity.apis.client.products.isabel_connect.services.PaymentNotificationService;
import com.ibanity.apis.client.services.ApiUrlProvider;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.HttpResponse;

import java.net.URI;

import static com.ibanity.apis.client.utils.URIHelper.buildUri;

public class PaymentNotificationServiceImpl implements PaymentNotificationService {
private final ApiUrlProvider apiUrlProvider;
private final IbanityHttpClient ibanityHttpClient;

public PaymentNotificationServiceImpl(ApiUrlProvider apiUrlProvider, IbanityHttpClient ibanityHttpClient) {
this.apiUrlProvider = apiUrlProvider;
this.ibanityHttpClient = ibanityHttpClient;
}

@Override
public IsabelCollection<PaymentNotification> list(PaymentNotificationsReadQuery query) {
URI uri = buildUri(getNotificationsUrl(), query.getPagingSpec());
HttpResponse response = ibanityHttpClient.get(uri, query.getAdditionalHeaders(), query.getAccessToken());
return IsabelModelMapper.mapCollection(response, PaymentNotification.class);
}

@Override
public void delete(PaymentNotificationDeleteQuery query) {
URI uri = buildUri(getNotificationUrl(query.getPaymentNotificationId()));
ibanityHttpClient.delete(uri, query.getAdditionalHeaders(), query.getAccessToken());
}

private String getNotificationsUrl() {
String url = apiUrlProvider
.find(IbanityProduct.IsabelConnect, "bulkPaymentInitiationRequests")
.replace("{bulkPaymentInitiationRequestId}", "notifications");
return StringUtils.removeEnd(url, "/");
}

private String getNotificationUrl(String paymentNotificationId) {
String url = apiUrlProvider
.find(IbanityProduct.IsabelConnect, "bulkPaymentInitiationRequests")
.replace("{bulkPaymentInitiationRequestId}", "notifications/" + paymentNotificationId);
return StringUtils.removeEnd(url, "/");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
package com.ibanity.apis.client.products.isabel_connect.services.impl;

import com.ibanity.apis.client.http.IbanityHttpClient;
import com.ibanity.apis.client.models.IbanityProduct;
import com.ibanity.apis.client.products.isabel_connect.models.read.IsabelPagingSpec;
import com.ibanity.apis.client.products.isabel_connect.models.read.PaymentStatusReadQuery;
import com.ibanity.apis.client.products.isabel_connect.services.PaymentStatusService;
import com.ibanity.apis.client.services.ApiUrlProvider;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.HttpResponse;

import java.io.IOException;
import java.net.URI;
import java.util.HashMap;
import java.util.Map;

import static com.ibanity.apis.client.mappers.ModelMapperHelper.readResponseContent;
import static com.ibanity.apis.client.utils.URIHelper.buildUri;

public class PaymentStatusServiceImpl implements PaymentStatusService {
private final ApiUrlProvider apiUrlProvider;
private final IbanityHttpClient ibanityHttpClient;

public PaymentStatusServiceImpl(ApiUrlProvider apiUrlProvider, IbanityHttpClient ibanityHttpClient) {
this.apiUrlProvider = apiUrlProvider;
this.ibanityHttpClient = ibanityHttpClient;
}

@Override
public String find(PaymentStatusReadQuery query) {
Map<String, String> queryParams = new HashMap<>();
if (StringUtils.isNotBlank(query.getNotificationId())) {
queryParams.put("notificationId", query.getNotificationId());
}
IsabelPagingSpec emptyPagingSpec = IsabelPagingSpec.builder().size(null).build();
URI uri = buildUri(getUrl(query.getBulkPaymentInitiationRequestId()), emptyPagingSpec, queryParams);
HttpResponse response = ibanityHttpClient.get(uri, query.getAdditionalHeaders(), query.getAccessToken());
try {
return readResponseContent(response.getEntity());
} catch (IOException exception) {
throw new IllegalArgumentException("Response cannot be parsed", exception);
}
}

private String getUrl(String bulkPaymentInitiationRequestId) {
String url = apiUrlProvider
.find(IbanityProduct.IsabelConnect, "bulkPaymentInitiationRequests")
.replace("{bulkPaymentInitiationRequestId}", bulkPaymentInitiationRequestId);
return StringUtils.removeEnd(url, "/") + "/payment-status";
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
package com.ibanity.apis.client.products.isabel_connect.services.impl;

import com.ibanity.apis.client.http.IbanityHttpClient;
import com.ibanity.apis.client.models.IbanityProduct;
import com.ibanity.apis.client.models.IsabelCollection;
import com.ibanity.apis.client.products.isabel_connect.models.PaymentNotification;
import com.ibanity.apis.client.products.isabel_connect.models.delete.PaymentNotificationDeleteQuery;
import com.ibanity.apis.client.products.isabel_connect.models.read.PaymentNotificationsReadQuery;
import com.ibanity.apis.client.services.ApiUrlProvider;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;
import org.mockito.junit.jupiter.MockitoSettings;
import org.mockito.quality.Strictness;

import java.net.URI;
import java.util.Collections;

import static com.ibanity.apis.client.helpers.IbanityTestHelper.createHttpResponse;
import static com.ibanity.apis.client.helpers.IbanityTestHelper.loadHttpResponse;
import static org.assertj.core.api.AssertionsForClassTypes.assertThat;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

@ExtendWith(MockitoExtension.class)
@MockitoSettings(strictness = Strictness.LENIENT)
public class PaymentNotificationServiceImplTest {
private static final String ACCESS_TOKEN = "thisIsAnAccessToken";
private static final String BPIR_ENDPOINT = "https://api.ibanity.localhost/isabel-connect/bulk-payment-initiation-requests/{bulkPaymentInitiationRequestId}";
private static final String LIST_ENDPOINT = "https://api.ibanity.localhost/isabel-connect/bulk-payment-initiation-requests/notifications?size=20";
private static final String NOTIFICATION_ID = "14e2bff5-e365-4bc7-bf48-76b7bcd464e9";
private static final String DELETE_ENDPOINT = "https://api.ibanity.localhost/isabel-connect/bulk-payment-initiation-requests/notifications/" + NOTIFICATION_ID;

@InjectMocks
private PaymentNotificationServiceImpl service;

@Mock
private ApiUrlProvider apiUrlProvider;

@Mock
private IbanityHttpClient ibanityHttpClient;

@BeforeEach
void setUp() {
when(apiUrlProvider.find(IbanityProduct.IsabelConnect, "bulkPaymentInitiationRequests"))
.thenReturn(BPIR_ENDPOINT);
}

@Test
public void list() throws Exception {
when(ibanityHttpClient.get(new URI(LIST_ENDPOINT), Collections.emptyMap(), ACCESS_TOKEN))
.thenReturn(loadHttpResponse("json/isabel-connect/payment_notifications.json"));

IsabelCollection<PaymentNotification> actual = service.list(PaymentNotificationsReadQuery.builder()
.accessToken(ACCESS_TOKEN)
.build());

assertThat(actual.getItems().size()).isEqualTo(1);
assertThat(actual.getPagingOffset()).isEqualTo(0);
assertThat(actual.getPagingTotal()).isEqualTo(1);

PaymentNotification notification = actual.getItems().get(0);
assertThat(notification.getId()).isEqualTo(NOTIFICATION_ID);
assertThat(notification.getNotificationType()).isEqualTo("payment.status.updated");
assertThat(notification.getCreatedAt()).isEqualTo("2026-06-04T14:30:00.000Z");
}

@Test
public void delete() throws Exception {
when(ibanityHttpClient.delete(new URI(DELETE_ENDPOINT), Collections.emptyMap(), ACCESS_TOKEN))
.thenReturn(createHttpResponse(""));

service.delete(PaymentNotificationDeleteQuery.builder()
.accessToken(ACCESS_TOKEN)
.paymentNotificationId(NOTIFICATION_ID)
.build());

verify(ibanityHttpClient).delete(new URI(DELETE_ENDPOINT), Collections.emptyMap(), ACCESS_TOKEN);
}
}
Loading
Loading