未验证 提交 81a6193a 编写于 作者: J Jake Wharton 提交者: GitHub

Merge pull request #3070 from NightlyNexus/eric.2019-04-09.headers-parameter

Support okhttp3.Headers for HeadersMap parameters.
......@@ -20,7 +20,6 @@ import java.lang.reflect.Array;
import java.lang.reflect.Method;
import java.util.Map;
import javax.annotation.Nullable;
import okhttp3.Headers;
import okhttp3.MultipartBody;
import okhttp3.RequestBody;
......@@ -230,6 +229,23 @@ abstract class ParameterHandler<T> {
}
}
static final class Headers extends ParameterHandler<okhttp3.Headers> {
private final Method method;
private final int p;
Headers(Method method, int p) {
this.method = method;
this.p = p;
}
@Override void apply(RequestBuilder builder, @Nullable okhttp3.Headers headers) {
if (headers == null) {
throw Utils.parameterError(method, p, "Headers parameter must not be null.");
}
builder.addHeaders(headers);
}
}
static final class Field<T> extends ParameterHandler<T> {
private final String name;
private final Converter<T, String> valueConverter;
......@@ -300,10 +316,10 @@ abstract class ParameterHandler<T> {
static final class Part<T> extends ParameterHandler<T> {
private final Method method;
private final int p;
private final Headers headers;
private final okhttp3.Headers headers;
private final Converter<T, RequestBody> converter;
Part(Method method, int p, Headers headers, Converter<T, RequestBody> converter) {
Part(Method method, int p, okhttp3.Headers headers, Converter<T, RequestBody> converter) {
this.method = method;
this.p = p;
this.headers = headers;
......@@ -367,7 +383,7 @@ abstract class ParameterHandler<T> {
"Part map contained null value for key '" + entryKey + "'.");
}
Headers headers = Headers.of(
okhttp3.Headers headers = okhttp3.Headers.of(
"Content-Disposition", "form-data; name=\"" + entryKey + "\"",
"Content-Transfer-Encoding", transferEncoding);
......
......@@ -55,6 +55,7 @@ final class RequestBuilder {
private @Nullable HttpUrl.Builder urlBuilder;
private final Request.Builder requestBuilder;
private final Headers.Builder headersBuilder;
private @Nullable MediaType contentType;
private final boolean hasBody;
......@@ -73,7 +74,9 @@ final class RequestBuilder {
this.hasBody = hasBody;
if (headers != null) {
requestBuilder.headers(headers);
headersBuilder = headers.newBuilder();
} else {
headersBuilder = new Headers.Builder();
}
if (isFormEncoded) {
......@@ -98,10 +101,14 @@ final class RequestBuilder {
throw new IllegalArgumentException("Malformed content type: " + value, e);
}
} else {
requestBuilder.addHeader(name, value);
headersBuilder.add(name, value);
}
}
void addHeaders(Headers headers) {
headersBuilder.addAll(headers);
}
void addPathParam(String name, String value, boolean encoded) {
if (relativeUrl == null) {
// The relative URL is cleared when the first query parameter is set.
......@@ -245,12 +252,13 @@ final class RequestBuilder {
if (body != null) {
body = new ContentTypeOverridingRequestBody(body, contentType);
} else {
requestBuilder.addHeader("Content-Type", contentType.toString());
headersBuilder.add("Content-Type", contentType.toString());
}
}
return requestBuilder
.url(url)
.headers(headersBuilder.build())
.method(method, body);
}
......
......@@ -512,6 +512,10 @@ final class RequestFactory {
}
} else if (annotation instanceof HeaderMap) {
if (type == Headers.class) {
return new ParameterHandler.Headers(method, p);
}
validateResolvableType(p, type);
Class<?> rawParameterType = Utils.getRawType(type);
if (!Map.class.isAssignableFrom(rawParameterType)) {
......
......@@ -15,9 +15,6 @@
*/
package retrofit2.http;
import static java.lang.annotation.ElementType.PARAMETER;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
import java.lang.annotation.Annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
......@@ -26,11 +23,15 @@ import java.lang.reflect.Type;
import java.util.Map;
import retrofit2.Retrofit;
import static java.lang.annotation.ElementType.PARAMETER;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
/**
* Adds headers specified in the {@link Map}.
* Adds headers specified in the {@link Map} or {@link okhttp3.Headers}.
* <p>
* Values are converted to strings using {@link Retrofit#stringConverter(Type, Annotation[])}
* (or {@link Object#toString()}, if no matching string converter is installed).
* Values in the map are converted to strings using
* {@link Retrofit#stringConverter(Type, Annotation[])} (or {@link Object#toString()}, if no
* matching string converter is installed).
* <p>
* Simple Example:
* <pre>
......
......@@ -60,6 +60,7 @@ import retrofit2.http.QueryName;
import retrofit2.http.Tag;
import retrofit2.http.Url;
import static java.util.Arrays.asList;
import static java.util.Collections.emptyList;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertNull;
......@@ -653,6 +654,70 @@ public final class RequestFactoryTest {
}
}
@Test public void getWithHeaders() {
class Example {
@GET("/search")
Call<ResponseBody> method(@HeaderMap okhttp3.Headers headers) {
throw new AssertionError();
}
}
okhttp3.Headers headers = new okhttp3.Headers.Builder()
.add("Accept", "text/plain")
.add("Accept", "application/json")
.add("Accept-Charset", "utf-8")
.build();
Request request = buildRequest(Example.class, headers);
assertThat(request.method()).isEqualTo("GET");
assertThat(request.url().toString()).isEqualTo("http://example.com/search");
assertThat(request.body()).isNull();
assertThat(request.headers().size()).isEqualTo(3);
assertThat(request.headers("Accept")).isEqualTo(asList("text/plain", "application/json"));
assertThat(request.header("Accept-Charset")).isEqualTo("utf-8");
}
@Test public void getWithHeadersAndHeaderMap() {
class Example {
@GET("/search")
Call<ResponseBody> method(@HeaderMap okhttp3.Headers headers,
@HeaderMap Map<String, Object> headerMap) {
throw new AssertionError();
}
}
okhttp3.Headers headers = new okhttp3.Headers.Builder()
.add("Accept", "text/plain")
.add("Accept-Charset", "utf-8")
.build();
Map<String, String> headerMap = Collections.singletonMap("Accept", "application/json");
Request request = buildRequest(Example.class, headers, headerMap);
assertThat(request.method()).isEqualTo("GET");
assertThat(request.url().toString()).isEqualTo("http://example.com/search");
assertThat(request.body()).isNull();
assertThat(request.headers().size()).isEqualTo(3);
assertThat(request.headers("Accept")).isEqualTo(asList("text/plain", "application/json"));
assertThat(request.header("Accept-Charset")).isEqualTo("utf-8");
}
@Test public void headersRejectsNull() {
class Example {
@GET("/")
Call<ResponseBody> method(@HeaderMap okhttp3.Headers headers) {
throw new AssertionError();
}
}
try {
buildRequest(Example.class, (okhttp3.Headers) null);
fail();
} catch (IllegalArgumentException e) {
assertThat(e).hasMessage("Headers parameter must not be null. (parameter #1)\n" +
" for method Example.method");
}
}
@Test public void twoBodies() {
class Example {
@PUT("/") //
......@@ -1889,7 +1954,7 @@ public final class RequestFactoryTest {
MultipartBody.Part part1 = MultipartBody.Part.createFormData("foo", "bar");
MultipartBody.Part part2 = MultipartBody.Part.createFormData("kit", "kat");
Request request = buildRequest(Example.class, Arrays.asList(part1, part2));
Request request = buildRequest(Example.class, asList(part1, part2));
assertThat(request.method()).isEqualTo("POST");
assertThat(request.headers().size()).isZero();
assertThat(request.url().toString()).isEqualTo("http://example.com/foo/bar/");
......@@ -1979,7 +2044,7 @@ public final class RequestFactoryTest {
}
}
Request request = buildRequest(Example.class, Arrays.asList("pong1", "pong2"));
Request request = buildRequest(Example.class, asList("pong1", "pong2"));
assertThat(request.method()).isEqualTo("POST");
assertThat(request.headers().size()).isZero();
assertThat(request.url().toString()).isEqualTo("http://example.com/foo/bar/");
......@@ -2622,7 +2687,7 @@ public final class RequestFactoryTest {
return null;
}
}
Request request = buildRequest(Example.class, Arrays.asList("bar", null, "baz"));
Request request = buildRequest(Example.class, asList("bar", null, "baz"));
assertThat(request.method()).isEqualTo("GET");
okhttp3.Headers headers = request.headers();
assertThat(headers.size()).isEqualTo(2);
......@@ -2897,7 +2962,7 @@ public final class RequestFactoryTest {
}
}
List<String> strings = Arrays.asList("tag", "value");
List<String> strings = asList("tag", "value");
Request request = buildRequest(Example.class, strings);
assertThat(request.tag(List.class)).isSameAs(strings);
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册