2015-09-16 32 views
55

Retrofit 2's documentation mówi:Dodawanie nagłówka do wszystkich prośbę z modernizacją 2

Nagłówki, które muszą być dodane do każdego żądania można określić za pomocą OkHttp przechwytujących.

Można to zrobić łatwo przy użyciu poprzedniej wersji, here's pokrewnej kontroli jakości.

Ale używając retrofitu 2, nie mogłem znaleźć czegoś takiego jak setRequestInterceptor lub setInterceptor metoda, którą można zastosować do obiektu Retrofit.Builder.

Wydaje się również, że nie ma już RequestInterceptor w OkHttp. Dokument Retrofit odsyła nas do Interceptor, którego nie bardzo rozumiałem, jak go używać w tym celu.

Jak mogę to zrobić?

Odpowiedz

102
OkHttpClient httpClient = new OkHttpClient.Builder(); 

httpClient.addInterceptor(new Interceptor() { 
    @Override 
    public Response intercept(Chain chain) throws IOException { 
     Request request = chain.request().newBuilder().addHeader("parameter", "value").build(); 
     return chain.proceed(request); 
    } 
}); 
Retrofit retrofit = new Retrofit.Builder().addConverterFactory(GsonConverterFactory.create()).baseUrl(url).client(httpClient.build()).build(); 
+5

W wersji retrofit2-beta3 jest nieco inaczej. Zobacz tutaj: http://stackoverflow.com/questions/34973432/okhttpclient-throws-exception-after-upgrading-to-okhttp3 –

+0

Jak możemy potwierdzić, że te nagłówki są wysyłane. Kiedy debuguję Call 'enqueue' nie widzę domyślnych nagłówków. – viper

+0

Powinien to być 'nowy OkHttpClient.Builder()' zamiast 'new OkHttpClient()' – Wojtek

46

Najnowsza wersja Retrofit TUTAJ -> 2.1.0. Wersja

lambda:

builder.addInterceptor(chain -> { 
    Request request = chain.request().newBuilder().addHeader("key", "value").build(); 
    return chain.proceed(request); 
    }); 

brzydki wersja długa:

builder.addInterceptor(new Interceptor() { 
    @Override public Response intercept(Chain chain) throws IOException { 
     Request request = chain.request().newBuilder().addHeader("key", "value").build(); 
     return chain.proceed(request); 
    } 
    }); 

pełną wersję:

class Factory { 

public static APIService create(Context context) { 

    OkHttpClient.Builder builder = new OkHttpClient().newBuilder(); 
    builder.readTimeout(10, TimeUnit.SECONDS); 
    builder.connectTimeout(5, TimeUnit.SECONDS); 

    if (BuildConfig.DEBUG) { 
    HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor(); 
    interceptor.setLevel(HttpLoggingInterceptor.Level.BASIC); 
    builder.addInterceptor(interceptor); 
    } 

    builder.addInterceptor(chain -> { 
    Request request = chain.request().newBuilder().addHeader("key", "value").build(); 
    return chain.proceed(request); 
    }); 

    builder.addInterceptor(new UnauthorisedInterceptor(context)); 
    OkHttpClient client = builder.build(); 

    Retrofit retrofit = 
     new Retrofit.Builder().baseUrl(APIService.ENDPOINT).client(client).addConverterFactory(GsonConverterFactory.create()).addCallAdapterFactory(RxJavaCallAdapterFactory.create()).build(); 

    return retrofit.create(APIService.class); 
    } 
} 

Gradle plik (trzeba dodać przechwytywania rejestrowania jeśli planujesz go używać):

//----- Retrofit 
    compile 'com.squareup.retrofit2:retrofit:2.1.0' 
    compile "com.squareup.retrofit2:converter-gson:2.1.0" 
    compile "com.squareup.retrofit2:adapter-rxjava:2.1.0" 
    compile 'com.squareup.okhttp3:logging-interceptor:3.4.0' 
2

w moim przypadku addInterceptor() nie działa, aby dodać nagłówki HTTP do mojego wniosku, musiałem użyć addNetworkInterceptor(). Kod jest następujący:

OkHttpClient.Builder httpClient = new OkHttpClient.Builder(); 
httpClient.addNetworkInterceptor(new AddHeaderInterceptor()); 

I kod przechwytujących:

public class AddHeaderInterceptor implements Interceptor { 
    @Override 
    public Response intercept(Chain chain) throws IOException { 

     Request.Builder builder = chain.request().newBuilder(); 
     builder.addHeader("Authorization", "MyauthHeaderContent"); 

     return chain.proceed(builder.build()); 
    } 
} 

Ten i inne przykłady na this gist

9

do logowania żądania i odpowiedzi potrzebujesz przechwytywania, a także do ustawiania nagłówka potrzebujesz przechwytywacza, Oto rozwiązanie polegające na dodaniu jednocześnie przechwytywacza za pomocą modernizacji 2.1

public OkHttpClient getHeader(final String authorizationValue) { 
     HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor(); 
     interceptor.setLevel(HttpLoggingInterceptor.Level.BODY); 
     OkHttpClient okClient = new OkHttpClient.Builder() 
       .addInterceptor(interceptor) 
       .addNetworkInterceptor(
         new Interceptor() { 
          @Override 
          public Response intercept(Interceptor.Chain chain) throws IOException { 
           Request request = null; 
           if (authorizationValue != null) { 
            Log.d("--Authorization-- ", authorizationValue); 

            Request original = chain.request(); 
            // Request customization: add request headers 
            Request.Builder requestBuilder = original.newBuilder() 
              .addHeader("Authorization", authorizationValue); 

            request = requestBuilder.build(); 
           } 
           return chain.proceed(request); 
          } 
         }) 
       .build(); 
     return okClient; 

    } 

Teraz w obiekcie modernizacji dodać ten nagłówek w kliencie

Retrofit retrofit = new Retrofit.Builder() 
       .baseUrl(url) 
       .client(getHeader(authorizationValue)) 
       .addConverterFactory(GsonConverterFactory.create()) 
       .build(); 
1

Jeśli używasz metody addInterceptor for Dodaj HttpLoggingInterceptor, nie będzie zalogowaniu rzeczy, które dodane przez innych przechwytujących stosowanych później niż HttpLoggingInterceptor.

Na przykład: jeśli masz dwie przechwytujących „HttpLoggingInterceptor” i „AuthInterceptor” i HttpLoggingInterceptor zastosowano pierwszy, wtedy nie może wyświetlić http-params lub nagłówków, które ustawione przez AuthInterceptor.

OkHttpClient.Builder builder = new OkHttpClient.Builder() 
.addNetworkInterceptor(logging) 
.addInterceptor(new AuthInterceptor()); 

Rozwiązałem go, korzystając z metody addNetworkInterceptor.