Newer
Older
import it.inaf.ia2.gms.client.call.HttpClientWrapper;
import it.inaf.ia2.gms.client.call.MockedHttpClientWrapper;
import it.inaf.ia2.gms.client.model.Permission;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpRequest.BodyPublisher;
import java.net.http.HttpResponse;
import java.net.http.HttpResponse.BodySubscriber;
import java.net.http.HttpResponse.BodySubscribers;
import java.nio.ByteBuffer;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.Flow;
import java.util.concurrent.Flow.Subscriber;
import static org.junit.Assert.assertEquals;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.AdditionalMatchers;
import org.mockito.ArgumentMatcher;
import org.mockito.ArgumentMatchers;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import org.mockito.junit.MockitoJUnitRunner;
@RunWith(MockitoJUnitRunner.class)
public class GmsClientTest {
private static final String BASE_URL = "http://base-url";
private HttpClient httpClient;
private GmsClient client;
@Before
public void setUp() {
httpClient = mock(HttpClient.class);
HttpClientWrapper clientWrapper = new MockedHttpClientWrapper(BASE_URL, httpClient);
client = new GmsClient(BASE_URL);
client.httpClientWrapper = clientWrapper;
public void testGetMyGroups() {
String body = "LBT.INAF\n"
+ "LBT.AZ";
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(200, body));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
List<String> groups = client.getMyGroups("LBT.");
verify(httpClient, times(1)).sendAsync(endpointEq("GET", "search"), any());
assertEquals(2, groups.size());
assertEquals("INAF", groups.get(0));
assertEquals("AZ", groups.get(1));
public void testListGroups() {
String body = "INAF\n"
+ "AZ";
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(200, body));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
List<String> groups = client.listGroups("LBT.");
verify(httpClient, times(1)).sendAsync(endpointEq("GET", "list/LBT."), any());
assertEquals(2, groups.size());
assertEquals("INAF", groups.get(0));
assertEquals("AZ", groups.get(1));
public void testCreateGroup() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(201));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
client.createGroup("LBT.INAF", false);
verify(httpClient, times(1)).sendAsync(endpointEq("POST", "LBT.INAF"), any());
}
@Test
public void testDeleteGroup() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(204));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
client.deleteGroup("LBT.INAF");
verify(httpClient, times(1)).sendAsync(endpointEq("DELETE", "LBT.INAF"), any());
public void testAddMember() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(200));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
client.addMember("LBT.INAF", "user");
verify(httpClient, times(1)).sendAsync(endpointEq("POST", "membership/LBT.INAF"), any());
public void testRemoveMember() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(204));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
client.removeMember("LBT.INAF", "user");
verify(httpClient, times(1)).sendAsync(endpointEq("DELETE", "membership/LBT.INAF?user_id=user"), any());
}
@Test
public void testAddPermission() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(200));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
client.addPermission("LBT.INAF", "user", Permission.ADMIN);
verify(httpClient, times(1)).sendAsync(endpointEq("POST", "permission/LBT.INAF"), any());
public void testRemovePermission() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(204));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
client.removePermission("LBT.INAF", "user");
verify(httpClient, times(1)).sendAsync(endpointEq("DELETE", "permission/LBT.INAF?user_id=user"), any());
}
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
@Test
public void testInvitedRegistration() {
CompletableFuture response = CompletableFuture.completedFuture(getMockedResponse(201));
when(httpClient.sendAsync(any(), any())).thenReturn(response);
Map<String, Permission> permissionsMap = new HashMap<>();
permissionsMap.put("group1", Permission.MANAGE_MEMBERS);
permissionsMap.put("group2", Permission.MANAGE_MEMBERS);
client.addInvitedRegistration("bvjsgqu423", "email", permissionsMap);
// hash = AOyojiwaRR7BHPde6Tomg3+BMoQQggNM3wUHEarXuNQ=
verify(httpClient, times(1)).sendAsync(
AdditionalMatchers.and(
endpointEq("POST", "invited-registration"),
ArgumentMatchers.argThat(req -> {
String reqbody = req.bodyPublisher().map(p -> {
var bodySubscriber = BodySubscribers.ofString(StandardCharsets.UTF_8);
var flowSubscriber = new StringSubscriber(bodySubscriber);
p.subscribe(flowSubscriber);
return bodySubscriber.getBody().toCompletableFuture().join();
}).get();
// If the resulting hash contains a + symbol it has to be encoded to %2B,
// otherwise it will be interpreted as a space and wrong value will be
// stored into the database
String expectedBody = "token_hash=AOyojiwaRR7BHPde6Tomg3%2BBMoQQggNM3wUHEarXuNQ="
+ "&email=email&groups=group2 MANAGE_MEMBERS\n"
+ "group1 MANAGE_MEMBERS";
return reqbody.equals(expectedBody);
})), any());
}
/**
* Credit: https://stackoverflow.com/a/55816685/771431
*/
static final class StringSubscriber implements Flow.Subscriber<ByteBuffer> {
final BodySubscriber<String> wrapped;
StringSubscriber(BodySubscriber<String> wrapped) {
this.wrapped = wrapped;
}
@Override
public void onSubscribe(Flow.Subscription subscription) {
wrapped.onSubscribe(subscription);
}
@Override
public void onNext(ByteBuffer item) {
wrapped.onNext(List.of(item));
}
@Override
public void onError(Throwable throwable) {
wrapped.onError(throwable);
}
@Override
public void onComplete() {
wrapped.onComplete();
}
}
private HttpResponse getMockedResponse(int statusCode, String body) {
HttpResponse response = getMockedResponse(statusCode);
InputStream in = new ByteArrayInputStream(body.getBytes(StandardCharsets.UTF_8));
when(response.body()).thenReturn(in);
return response;
private HttpResponse getMockedResponse(int statusCode) {
HttpResponse response = mock(HttpResponse.class);
when(response.statusCode()).thenReturn(statusCode);
return response;
private HttpRequest endpointEq(String expectedMethod, String expectedEndpoint) {
return ArgumentMatchers.argThat(endpointEqArgumentMatcher(expectedMethod, expectedEndpoint));
}
private ArgumentMatcher<HttpRequest> endpointEqArgumentMatcher(String expectedMethod, String expectedEndpoint) {
return new ArgumentMatcher<HttpRequest>() {
private final String expectedUri = BASE_URL + "/" + expectedEndpoint;
@Override
public boolean matches(HttpRequest request) {
return expectedMethod.equals(request.method()) && expectedUri.equals(request.uri().toString());
}
@Override
public String toString() {
return expectedMethod + " " + expectedUri;
}
};