2016-12-13 3 views
0

同じurlと異なるacceptヘッダで要求を行うと、okhttp cacheの前の応答が返されます。OkHttpクライアントはAcceptヘッダを尊重しません

これは、アプリケーション/ jsonデータに対して最初に要求が行われたことを意味し、2番目の要求はapplication/xmlを要求します。したがって、クライアントは上流からxmlを実行する代わりに、キャッシュからjsonデータを返します。

たとえば、GETリクエスト:http://example.comとheader application/jsonを指定すると、Cache-Controlヘッダーとjsonペイロードが返されます。 レスポンスが内部のhttpキャッシュにキャッシュされます。 2番目の要求は、cache-controlウィンドウ内で、header application/xmlを使用してhttp://example.comになります。この場合、Okhttpはxmlペイロードではなく、同じjsonペイロードをキャッシュから返します。

Builder builder = new Builder().url("https://httpbin.org/headers").header("accept", header); 

この問題は既に経験したことがありますか?キャッシュがどのように動作するかを説明し

+1

短いコードを出力して、問題を実証しているかもしれませんか? – slim

+0

https://gist.github.com/gpor89/c69c795b334af5ff63cef6468222a01eサイトがキャッシュヘッダーを返さないため、このリソースはテストに合格します。 – Gregor

+0

要注意です。質問は自己完結型でなければなりません。あなたはコード全体を必要とせず、人々があなたがしていることを見ることができるだけで、あなたの出力を表示することができます。 – slim

答えて

2

関連するRFCは、ここにある:https://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html#sec13.6

キャッシュされたエントリのための選択要求ヘッダフィールドは、その後、新しい要求の選択要求ヘッダフィールドと一致しない場合キャッシュは、条件付き要求で元のサーバーに新しい要求を最初に中継し、サーバーがエンティティタグまたはContent-Locationを含む304(Not Modified)で応答しない限り、キャッシュされたエントリを使用してはなりません(MUST NOT)。利用される。

OkHttpのCacheにソースコードはここにある:https://github.com/square/okhttp/blob/master/okhttp/src/main/java/okhttp3/Cache.java

キャッシュキーは、単にリソースのURLです。しかし、キャッシュエントリは、あまりにも「異なる」リクエストヘッダと比較さ:

Response response = entry.response(snapshot); 

if (!entry.matches(request, response)) { 
    Util.closeQuietly(response.body()); 
    return null; 
} 

...

public boolean matches(Request request, Response response) { 
    return url.equals(request.url().toString()) 
     && requestMethod.equals(request.method()) 
     && HttpHeaders.varyMatches(response, varyHeaders, request); 
} 

それはおそらく、あなたはもちろん、バグを見つけたです。私は、OkHttpソースJARを取り込み、Cache.get()メソッドのブレークポイントでデバッグし、間違っているかどうかを調べるステップを実行することをお勧めします。そうであれば、保守担当者に提出するか、パッチを提出してください。

+2

_key_はURLにすぎませんが、キャッシュされた応答を返すかどうかを決定する際に、格納されている応答と着信要求からヘッダーを考慮します。 –

+0

@JesseWilsonああ、近くに見て、そうする。 – slim

+1

@JesseWilsonはそれに応じて答えを変更しました。 – slim

関連する問題