Skip to content
This repository has been archived by the owner on Sep 28, 2021. It is now read-only.

Commit

Permalink
add flatMapPayload(Fn<A,Response<B>>) to Response
Browse files Browse the repository at this point in the history
  • Loading branch information
rouzwawi committed Nov 30, 2015
1 parent 706254c commit 61517a3
Show file tree
Hide file tree
Showing 2 changed files with 82 additions and 0 deletions.
36 changes: 36 additions & 0 deletions apollo-api/src/main/java/com/spotify/apollo/Response.java
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,42 @@ default <P> Response<P> mapPayload(Function<? super T, ? extends P> mapFunction)
: withPayload(mapFunction.apply(payload().get()));
}

/**
* Maps the contained payload if it exists, otherwise does nothing except changing the type
* of the response.
*
* The new response contents will be merged with this response using {@link #merge(Response)}.
*
* @param mapFunction The function for mapping the payload
* @param <P> The type of the mapped payload
* @return A response with a converted payload
*/
default <P> Response<P> flatMapPayload(Function<? super T, ? extends Response<? extends P>> mapFunction) {
//noinspection unchecked
return !payload().isPresent()
? (Response<P>) this
: merge(mapFunction.apply(payload().get()));
}

/**
* Merge another response with this response.
*
* The payload of the other response will override the payload in this response,
* even if not present, in which case it will reset the payload.
*
* Headers keys will be merged with headers from the other response taking precedence.
*
* The status of the other response will always be ignored.
*
* @param other The other response to merge with this
* @param <P> The type of the other response payload
* @return A merged response
*/
default <P> Response<P> merge(Response<? extends P> other) {
return withPayload(other.payload().orElse(null))
.withHeaders(other.headers());
}

/**
* Returns a typed 200 OK {@link Response}.
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,11 +57,57 @@ public void mapsPayload(Response<String> input) throws Exception {
}
}

@Theory
public void removePayloadIfNull(Response<String> input) throws Exception {
Response<Integer> intResponse = input.mapPayload(ignored -> null);

assertFalse(intResponse.payload().isPresent());
}

@Theory
public void preserveStatusAndHeaderOnMap(Response<String> input) throws Exception {
Response<Integer> intResponse = input.mapPayload(String::length);

assertThat(intResponse.status(), is(Status.IM_A_TEAPOT));
assertThat(intResponse.headers(), hasEntry("foo", "bar"));
}

@Theory
public void mapsPayloadOnFlatMap(Response<String> input) throws Exception {
Response<Integer> intResponse = input.flatMapPayload(
str -> Response.forPayload(str.length()));

if (input.payload().isPresent()) {
assertThat(intResponse.payload().get().intValue(), is(5));
} else {
assertFalse(intResponse.payload().isPresent());
}
}

@Theory
public void mergesHeadersOnFlatMap(Response<String> input) throws Exception {
Response<Integer> intResponse = input.flatMapPayload(
str -> Response.forPayload(str.length())
.withHeader("baz", str));

assertThat(intResponse.headers(), hasEntry("foo", "bar"));
if (input.payload().isPresent()) {
assertThat(intResponse.headers(), hasEntry("baz", "hello"));
}
}

@Theory
public void preservesStatusOnFlatMap(Response<String> input) throws Exception {
Response<Integer> intResponse = input.flatMapPayload(
ignored -> Response.forStatus(Status.GONE));

assertThat(intResponse.status(), is(Status.IM_A_TEAPOT));
}

@Theory
public void removePayloadIfNotSetOnFlatMap(Response<String> input) throws Exception {
Response<Integer> intResponse = input.flatMapPayload(ignored -> Response.ok());

assertFalse(intResponse.payload().isPresent());
}
}

0 comments on commit 61517a3

Please sign in to comment.