141

完全な要求/応答本文をログに記録するための関連するメソッドが Retrofit API に見つかりません。プロファイラーで何らかの助けが得られることを期待していました (ただし、応答に関するメタデータのみが提供されます)。ビルダーでログレベルを設定しようとしましたが、これも役に立ちません:

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

編集: このコードは現在機能しています。なぜそれが以前に機能しなかったのかわかりません。おそらく、古いバージョンのレトロフィットを使用していたためです。

4

13 に答える 13

137

レトロフィット 2.0 :

更新: @by Marcus Pöhls

ログイン Retrofit 2

Retrofit 2 は、あらゆるネットワーク操作を完全に OkHttp に依存しています。OkHttp は Retrofit 2 のピア依存関係であるため、Retrofit 2 が安定版リリースとしてリリースされたら、依存関係を追加する必要はありません。

OkHttp 2.6.0 には内部依存関係としてログ インターセプターが付属しており、Retrofit クライアントで直接使用できます。Retrofit 2.0.0-beta2 は引き続き OkHttp 2.5.0 を使用します。今後のリリースでは、依存関係をより高い OkHttp バージョンに引き上げる予定です。そのため、ロギング インターセプターを手動でインポートする必要があります。次の行を build.gradle ファイル内の gradle インポートに追加して、ロギング インターセプターの依存関係をフェッチします。

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

このインターセプターについては、Square の GitHub ページにもアクセスできます。

Retrofit 2 にロギングを追加する

アプリの開発中やデバッグ目的で、ログ機能を統合してリクエストとレスポンスの情報を表示すると便利です。Retrofit 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 の 4 つのログ レベルがあります。各ログ レベルについて説明し、その出力について説明します。

詳細については、次を参照してください: Retrofit 2 — ログの要求と応答

古い答え:

Retrofit 2 にログインしなくなりました。開発チームはログ機能を削除しました。正直なところ、ログ機能はそれほど信頼できるものではありませんでした。Jake Wharton は、ログに記録されたメッセージまたはオブジェクトは想定された値であり、それらが真であることを証明できないと明示的に述べました。サーバーに到着する実際のリクエストは、変更されたリクエストボディまたは何か他のものを持っている可能性があります。

デフォルトでは統合ロギングはありませんが、任意の Java ロガーを活用して、カスタマイズされた OkHttp インターセプター内で使用できます。

Retrofit 2 の詳細については、次を参照してください: Retrofit — Getting Started and Create an Android Client

于 2015-10-25T10:16:04.413 に答える
94

使用setLogLevel(LogLevel.FULL).setLog(new AndroidLog("YOUR_LOG_TAG"))しました、助かりました。
アップデート。応答モデルとして
デバッグ目的で使用することもできますretrofit.client.Response

于 2014-03-26T08:29:04.350 に答える
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 ]

カスタムフィルターを調整することで、ベーシック+ボディを簡単にログに記録できるはずです。私はブラックリストを使用していますが、必要に応じてホワイトリストを使用することもできます。

于 2015-02-25T17:52:53.670 に答える
3

理想的には、Timberを使用する場合は、ログ メッセージをファイルに保存するなど、アプリ内のログ メッセージをグローバルに処理できるため、より優れています。Httplogginginterceptor を木材で動作させる方法は次のとおりです。

val loggingInterceptor = HttpLoggingInterceptor { message -> 
Timber.d(message) 
}.apply {
     level = HttpLoggingInterceptor.Level.BODY
}

val client = OkHttpClient.Builder()
            .addInterceptor(loggingInterceptor)
            .build()

return Retrofit.Builder()
            .baseUrl(baseUrl)
            .addConverterFactory(GsonConverterFactory.create())
            .client(client)
            .build()
            .create(RetrofitApiService::class.java)

次の方法で、ロガー インターセプターの独自の実装を作成することもできます。

class HttpLoggingInterceptor : Interceptor {
    override fun intercept(chain: Interceptor.Chain): Response {
        val request: Request = chain.request()

        val t1 = System.nanoTime()
        Timber.i(
            "Sending request %s on %s%n%s",
            request.url,
            chain.connection(),
            request.headers
        )
        Timber.v("REQUEST BODY BEGIN\n%s\nREQUEST BODY END", bodyToString(request))

        val response = chain.proceed(request)

        val responseBody: ResponseBody? = response.body
        val responseBodyString = response.body!!.string()

        val newResponse = response.newBuilder()
            .body(responseBodyString.toResponseBody(responseBody?.contentType()))
            .build()

        val t2 = System.nanoTime()
        Timber.i(
            "Received response for %s in %.1fms%n%s",
            response.request.url,
            (t2 - t1) / 1e6,
            response.headers
        )
        Timber.v("RESPONSE BODY BEGIN:\n%s\nRESPONSE BODY END", responseBodyString)

        return newResponse
    }

    private fun bodyToString(request: Request): String? {
        return try {
            val copy = request.newBuilder().build()
            val buffer = Buffer()
            copy.body!!.writeTo(buffer)
            buffer.readUtf8()
        } catch (e: Exception) {
            "did not work"
        }
    }
}
于 2021-08-13T13:28:07.613 に答える