Retrofit-Android के साथ अनुरोध और प्रतिक्रिया निकाय लॉग कैसे करें?


129

मुझे पूर्ण अनुरोध / प्रतिक्रिया निकायों को लॉग करने के लिए रेट्रोफ़िट एपीआई में प्रासंगिक तरीके नहीं मिल सकते हैं। मैं प्रोइलर में कुछ मदद की उम्मीद कर रहा था (लेकिन यह केवल प्रतिक्रिया के बारे में मेटा-डेटा प्रदान करता है)। मैंने बिल्डर में लॉग स्तर सेट करने की कोशिश की, लेकिन इससे मुझे मदद नहीं मिली:

RestAdapter adapter = (new RestAdapter.Builder()).
                setEndpoint(baseUrl).
                setRequestInterceptor(interceptor).
                setProfiler(profiler).
                setClient(client).
                setExecutors(MyApplication.getWebServiceThreadPool()).
                setLogLevel(LogLevel.FULL).
                setLog(new RestAdapter.Log() {
                    @Override
                    public void log(String msg) {
                        Log.i(TAG, msg);
                    }
                }).
                build();

EDIT: यह कोड अब काम कर रहा है। मुझे नहीं पता कि यह पहले क्यों काम नहीं कर रहा था। संभवतः इसलिए कि मैं पुराने समय के कुछ पुराने संस्करण का उपयोग कर रहा था।


क्या आपको इसका कभी पता चला? प्रलेखन का कहना है कि FULLशरीर को देने वाला है लेकिन ऐसा प्रतीत नहीं होता है।
दिबांग

1
@mattblang: मुझे नहीं पता कि पहले क्या गलत था, लेकिन यह कोड अब काम कर रहा है।
जगुआर



संभवत: तत्काल रन गड़बड़ कर दिया है अगर यह पहले काम नहीं किया
deathangel908

जवाबों:


91

मैंने इस्तेमाल किया setLogLevel(LogLevel.FULL).setLog(new AndroidLog("YOUR_LOG_TAG")), इससे मुझे मदद मिली।
अपडेट करें।
आप retrofit.client.Responseप्रतिक्रिया मॉडल के रूप में डिबग उद्देश्य उपयोग के लिए भी प्रयास कर सकते हैं


2
AndroidLogक्या कक्षा है?
दिबांग

यह रेट्रोफिट लाइब्रेरी के साथ आता है।
एलेक्स डिज़ेश्को

2
समझा। दुर्भाग्य से यह आपको नहीं देता है response body, हालांकि यह डॉक्टर में राज्य करता है जो आपको देना LogLevel.FULL चाहिएresponse body
दिबांग

इसे वर्बोज़ टैब के तहत एंड्रॉइड लॉगकट में "Your_LOG_TAG" के साथ देखा जा सकता है।
राजेश

4
LogLevel.Full रेट्रोफिट 2 में मौजूद नहीं है

121

रेट्रोफिट 2.0 :

अद्यतन: @ मार्क मार्कस Pöhls

रेट्रोफिट 2 में लॉगिंग

Retrofit 2 पूरी तरह से किसी भी नेटवर्क ऑपरेशन के लिए OkHttp पर निर्भर करता है। चूंकि OkHttp Retrofit 2 की एक सहकर्मी निर्भरता है, इसलिए Retrofit 2 को एक स्थिर रिलीज़ के रूप में रिलीज़ होने के बाद आपको अतिरिक्त निर्भरता जोड़ने की आवश्यकता नहीं होगी।

OkHttp 2.6.0 जहाजों को एक आंतरिक निर्भरता के रूप में लॉगिंग इंटरसेप्टर के साथ और आप सीधे अपने रेट्रोफिट क्लाइंट के लिए इसका उपयोग कर सकते हैं। Retrofit 2.0.0-beta2 अभी भी OkHttp 2.5.0 का उपयोग करता है। भविष्य के रिलीज उच्च OkHttp संस्करणों के लिए निर्भरता को टक्कर देंगे। इसलिए आपको लॉगिंग इंटरसेप्टर को मैन्युअल रूप से आयात करने की आवश्यकता है। लॉगिंग इंटरसेप्टर निर्भरता लाने के लिए अपनी बिल्ड.gradle फ़ाइल के भीतर अपने ग्रेडेल आयात में निम्न पंक्ति जोड़ें।

compile 'com.squareup.okhttp3:logging-interceptor:3.9.0'

आप इस इंटरसेप्टर के बारे में स्क्वायर के गिटहब पेज पर भी जा सकते हैं

लॉगिंग को रेट्रोफिट 2 में जोड़ें

अपने ऐप को विकसित करने और डिबगिंग उद्देश्यों के लिए, अनुरोध और प्रतिक्रिया की जानकारी दिखाने के लिए एक लॉग सुविधा को एकीकृत करना अच्छा है। चूंकि रेट्रोफिट 2 में लॉगिंग अब डिफ़ॉल्ट रूप से एकीकृत नहीं है, इसलिए हमें OkHttp के लिए लॉगिंग इंटरसेप्टर जोड़ना होगा। सौभाग्य से OkHttp इस इंटरसेप्टर के साथ पहले से ही जहाज है और आपको केवल अपने OkHttpClient के लिए इसे सक्रिय करने की आवश्यकता है।

HttpLoggingInterceptor logging = new HttpLoggingInterceptor();  
// set your desired log level
logging.setLevel(HttpLoggingInterceptor.Level.BODY);
OkHttpClient.Builder httpClient = new OkHttpClient.Builder();   
// add your other interceptors …
// add logging as last interceptor
httpClient.addInterceptor(logging);  // <-- this is the important line!
Retrofit retrofit = new Retrofit.Builder()  
        .baseUrl(API_BASE_URL)
        .addConverterFactory(GsonConverterFactory.create())
        .client(httpClient.build())
        .build();

हम अंतिम इंटरसेप्टर के रूप में लॉगिंग को जोड़ने की सलाह देते हैं, क्योंकि यह आपके अनुरोध पर पिछले इंटरसेप्टर के साथ जोड़ी गई जानकारी को भी लॉग करेगा।

लॉग स्तर

लॉगिंग बहुत अधिक जानकारी आपके Android मॉनिटर को उड़ा देगी, यही कारण है कि OkHttp के लॉगिंग इंटरसेप्टर में चार लॉग स्तर हैं: NONE, BASIC, HEADERS, BODY। हम आपको लॉग स्तरों में से प्रत्येक के माध्यम से चलेंगे और उनके आउटपुट का वर्णन करेंगे।

अधिक जानकारी के लिए कृपया देखें: रेट्रोफ़िट 2 - लॉग अनुरोध और प्रतिक्रियाएं

पुराने उत्तर:

अब रेट्रोफिट 2 में कोई लॉगिंग नहीं है। विकास टीम ने लॉगिंग सुविधा को हटा दिया। ईमानदार होने के लिए, लॉगिंग सुविधा वैसे भी विश्वसनीय नहीं थी। जेक व्हार्टन ने स्पष्ट रूप से कहा कि लॉग किए गए संदेश या ऑब्जेक्ट मान हैं और उन्हें सत्य होने का प्रमाण नहीं दिया जा सकता है। सर्वर पर आने वाला वास्तविक अनुरोध एक परिवर्तित अनुरोध निकाय या कुछ और हो सकता है।

भले ही डिफ़ॉल्ट रूप से कोई एकीकृत लॉगिंग नहीं है, आप किसी भी जावा लकड़हारे का लाभ उठा सकते हैं और इसे एक अनुकूलित ओक्टेट इंटरसेप्टर के भीतर उपयोग कर सकते हैं।

Retrofit 2 के बारे में अधिक जानकारी कृपया देखें: रिट्रोफिट - आरंभ करना और Android क्लाइंट बनाना


1
रेट्रोफिट 2.0 में लॉगिंग के लिए एक पोस्ट विशिष्ट भी है: futurestud.io/blog/retrofit-2-log-requests-and-responses
peitek

हर चीज को उससे अधिक जटिल बनाने का शानदार तरीका होना चाहिए। जर्सी 1 बनाम जर्सी 2 लॉगिंग की याद दिलाता है। अधिक बॉयलरप्लेट कोड ....
ब्रेकलाइन

इस तरह से इंटरसेप्टर जोड़ने पर अब OkHttp v3 में एक UnsupportedOperationException होगी। नया तरीका है: OkHttpClient.Builder ()। AddInterceptor (logging .build) () github.com/square/okhttp/issues/2219
Amagi82

@JawadLeWywadi हाँ इस कोड का उपयोग करके आप शरीर को प्रिंट कर सकते हैं
धवल जिवानी

रेट्रोफिट 2 के लिए, यह बहुत आसान है।
गैरी 99

31

रेट्रॉफिट 2.0.0-बीटा 3 के लिए अपडेट

अब आपको बिल्डर के साथ okhttp3 का उपयोग करना होगा। साथ ही पुराना इंटरसेप्टर भी काम नहीं करेगा। यह प्रतिक्रिया एंड्रॉइड के लिए अनुकूलित है।

यहां आपके लिए नए सामान के साथ एक त्वरित कॉपी पेस्ट है।

1. अपनी gradle फ़ाइल को संशोधित करें

  compile 'com.squareup.retrofit2:retrofit:2.0.0-beta3'
  compile "com.squareup.retrofit2:converter-gson:2.0.0-beta3"
  compile "com.squareup.retrofit2:adapter-rxjava:2.0.0-beta3"
  compile 'com.squareup.okhttp3:logging-interceptor:3.0.1'

2. इस नमूना कोड की जाँच करें:

नए आयात के साथ। यदि आप इसका उपयोग नहीं करते हैं, तो आप Rx को हटा सकते हैं, जो आप उपयोग नहीं करते हैं उसे भी हटा दें।

import okhttp3.OkHttpClient;
import okhttp3.logging.HttpLoggingInterceptor;
import retrofit2.GsonConverterFactory;
import retrofit2.Retrofit;
import retrofit2.RxJavaCallAdapterFactory;
import retrofit2.http.GET;
import retrofit2.http.Query;
import rx.Observable;

public interface APIService {

  String ENDPOINT = "http://api.openweathermap.org";
  String API_KEY = "2de143494c0b2xxxx0e0";

  @GET("/data/2.5/weather?appid=" + API_KEY) Observable<WeatherPojo> getWeatherForLatLon(@Query("lat") double lat, @Query("lng") double lng, @Query("units") String units);


  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);
      }

      //Extra Headers

      //builder.addNetworkInterceptor().add(chain -> {
      //  Request request = chain.request().newBuilder().addHeader("Authorization", authToken).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);
    }
  }
}

बक्शीश

मुझे पता है कि यह अपमानजनक है लेकिन मुझे यह अच्छा लगता है।

अनधिकृत के http त्रुटि कोड होने की स्थिति में , यहां एक इंटरसेप्टर है। मैं ईवेंट को प्रसारित करने के लिए ईवेंटबस का उपयोग करता हूं।

import android.content.Context;
import android.os.Handler;
import android.os.Looper;
import com.androidadvance.ultimateandroidtemplaterx.BaseApplication;
import com.androidadvance.ultimateandroidtemplaterx.events.AuthenticationErrorEvent;

import de.greenrobot.event.EventBus;
import java.io.IOException;
import javax.inject.Inject;
import okhttp3.Interceptor;
import okhttp3.Response;

public class UnauthorisedInterceptor implements Interceptor {

  @Inject EventBus eventBus;

  public UnauthorisedInterceptor(Context context) {
    BaseApplication.get(context).getApplicationComponent().inject(this);
  }

  @Override public Response intercept(Chain chain) throws IOException {
    Response response = chain.proceed(chain.request());
    if (response.code() == 401) {
      new Handler(Looper.getMainLooper()).post(() -> eventBus.post(new AuthenticationErrorEvent()));
    }
    return response;
  }
}

कोड https://github.com/AndreiD/UltimateAndroidTemplateRx (मेरी परियोजना) से लें।


9

वहाँ बुनियादी + शरीर करने का एक तरीका प्रतीत नहीं होता है, लेकिन आप FULL का उपयोग कर सकते हैं और उन हेडर को फ़िल्टर कर सकते हैं जिन्हें आप नहीं चाहते हैं।

RestAdapter adapter = new RestAdapter.Builder()
                          .setEndpoint(syncServer)
                          .setErrorHandler(err)
                          .setConverter(new GsonConverter(gson))
                          .setLogLevel(logLevel)
                          .setLog(new RestAdapter.Log() {
                              @Override
                              public void log(String msg) {
                                  String[] blacklist = {"Access-Control", "Cache-Control", "Connection", "Content-Type", "Keep-Alive", "Pragma", "Server", "Vary", "X-Powered-By"};
                                  for (String bString : blacklist) {
                                      if (msg.startsWith(bString)) {
                                          return;
                                      }
                                  }
                                  Log.d("Retrofit", msg);
                              }
                          }).build();

ऐसा प्रतीत होता है कि लॉग को ओवरराइड करते समय, शरीर एक टैग के समान उपसर्ग करता है

[ 02-25 10:42:30.317 25645:26335 D/Retrofit ]

इसलिए कस्टम फ़िल्टर को समायोजित करके बुनियादी + शरीर लॉग करना आसान होना चाहिए। मैं एक ब्लैकलिस्ट का उपयोग कर रहा हूं, लेकिन आपकी आवश्यकताओं के आधार पर एक श्वेतसूची का भी उपयोग किया जा सकता है।


4

नीचे कोड हेडर और बिना हेडर दोनों के लिए लॉग अनुरोध और प्रतिक्रिया प्रिंट करने के लिए काम कर रहा है। नोट: यदि आप हेडर का उपयोग नहीं कर रहे हैं तो बस .addHeader () लाइन पर टिप्पणी करें।

HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor();
        interceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
        OkHttpClient client = new OkHttpClient.Builder()
                .addInterceptor(interceptor)
                //.addInterceptor(REWRITE_CACHE_CONTROL_INTERCEPTOR)
                .addNetworkInterceptor(new Interceptor() {

                    @Override

                    public okhttp3.Response intercept(Chain chain) throws IOException {
                        Request request = chain.request().newBuilder()
                                // .addHeader(Constant.Header, authToken)
                                   .build();
                        return chain.proceed(request);
                    }
                }).build();

        final Retrofit retrofit = new Retrofit.Builder()
                .baseUrl(Constant.baseUrl)
                .client(client) // This line is important
                .addConverterFactory(GsonConverterFactory.create())
                .build();

3

मुझे उम्मीद है कि यह कोड आपको लॉग इन करने में मदद करेगा।
आपको बस अपने Build.Gradleबनाने में इंटरसेप्टर जोड़ने की जरूरत हैRetrofitClient

पहला कदम

इस लाइन को अपने में जोड़ें build.gradle

 implementation 'com.squareup.okhttp3:logging-interceptor:3.4.1' 

दूसरा कदम

अपना पुराना ग्राहक बनायें


   public class RetrofitClient {

    private Retrofit retrofit;
    private static OkHttpClient.Builder httpClient =
            new OkHttpClient.Builder();
    private static RetrofitClient instance = null;
    private static ApiServices service = null;
    private static HttpLoggingInterceptor logging =
            new HttpLoggingInterceptor();

    private RetrofitClient(final Context context) {
        httpClient.interceptors().add(new Interceptor() {
            @Override
            public okhttp3.Response intercept(Interceptor.Chain chain) throws IOException {
                Request originalRequest = chain.request();
                Request.Builder builder = originalRequest.newBuilder().
                        method(originalRequest.method(), originalRequest.body());
                okhttp3.Response response = chain.proceed(builder.build());
                /*
                Do what you want
                 */
                return response;
            }
        });

        if (BuildConfig.DEBUG) {
            logging.setLevel(HttpLoggingInterceptor.Level.BODY);
            // add logging as last interceptor
            httpClient.addInterceptor(logging);
        }

        retrofit = new Retrofit.Builder().client(httpClient.build()).
                baseUrl(Constants.BASE_URL).
                addConverterFactory(GsonConverterFactory.create()).build();
        service = retrofit.create(ApiServices.class);
    }


    public static RetrofitClient getInstance(Context context) {
        if (instance == null) {
            instance = new RetrofitClient(context);
        }
        return instance;
    }

    public ApiServices getApiService() {
        return service;
    }
}

कॉलिंग

RetrofitClient.getInstance(context).getApiService().yourRequestCall(); 

2

यदि आप Retrofit2 और okhttp3 का उपयोग कर रहे हैं तो आपको यह जानना होगा कि इंटरसेप्टर कतार द्वारा काम करता है। इसलिए अपने अन्य इंटरसेप्टर के बाद, अंत में loggingInterceptor जोड़ें:

HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor();
        if (BuildConfig.DEBUG)
            loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.HEADERS);

 new OkHttpClient.Builder()
                .connectTimeout(60, TimeUnit.SECONDS)
                .readTimeout(60, TimeUnit.SECONDS)
                .writeTimeout(60, TimeUnit.SECONDS)
                .addInterceptor(new CatalogInterceptor(context))
                .addInterceptor(new OAuthInterceptor(context))
                .authenticator(new BearerTokenAuthenticator(context))
                .addInterceptor(loggingInterceptor)//at the end
                .build();


0

3.0 से पहले एंड्रॉइड स्टूडियो के लिए (एंड्रॉइड मोटीनर का उपयोग करके)
https://futurestud.io/tutorials/retrofit-2-log-requests-and-responses
https://www.youtube.com/watch?v=vazLpz55y9M

और 3.0 से ऊपर के एंड्रॉइड स्टूडियो के लिए (एंड्रॉइड प्रोफाइलर के रूप में एंड्रॉइड मॉनिटर का उपयोग एंड्रॉइड प्रोफाइलर द्वारा बदल दिया जाता है)
https://futurestud.io/tutorials/retrofit-2-analyze-network-traffic-with-android-studio-profiler

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.