NSURLConnection seems to assume responses after calls with "If-Modified-Since"

Number:rdar://7869558 Date Originated:15-Apr-2010 02:13 PM
Status:Open Resolved:
Product:iPhone SDK Product Version:3.2
Classification:BUG Reproducible:Always
15-Apr-2010 02:13 PM Mike Pattee:
When making web service calls with NSURLConnection, requests that include "If-Modified-Since" in the header and return a status code of 304 cause subsequent calls to also return status code 304 erroneously and may not even submit all subsequent calls while still reporting a status code of 304 for a call that didn't happen.

Steps to Reproduce:
I've provided a sample application that shows this happening.
1. make 3 synchronous web service calls using NSURLConnection sendSynchronousRequest.
2. include the "If-Modified-Since" header field on the first request and it returns a status code 304
3. subsequent calls return status code 304 even if they don't actually attempt the request
4. if you add a small sleep between calls, the 2nd and 3rd calls will work as expected and return status code 200
5. if you remove the "If-Modified-Since" from the request header then all 3 calls return a 200.
6. server is always returning accurate status as seen in screenshots from HTTP Scoop

Expected Results:
the first calls 304 should not influence the subsequent calls. they should execute properly without needing to add a fake delay in between.

Actual Results:
first web service call correctly returns a 304, second web service call is made and returns a 200 to the system but reports a 304 in code, third call isn't made but reports a 304. 2nd and 3rd calls don't have the "If-Modified-Since" field and should never return 304. Server is actually returning 200 for the call that is made.

I've encountered an interesting issue with NSURLConnection and web services when the "If-Modified-Since" header field is used. I have three web service calls that executed during the startup of my application. Recently we added the "If-Modified-Since" fields to them to help speed up launch if the data on the server hadn't changed. What I noticed was that if the first of the three calls returns a 304 the subsequent calls will return 304's also even though thats not what is reported by the OS or the server being connected to. The status codes for the responses will indicate that they were 304's in code but that doesn't match with the packet sniffer tracking the traffic. I used HTTP Scoop to track the information being sent. Another oddity was that even though we received three 304 status codes for the three web service calls according to HTTP Scoop only two calls were made with one resulting in a 304 and the other in a 200. If I remove the "If-Modified-Since" header field then all 3 services work correctly with status 200's and show up correctly in HTTP Scoop. Another oddity is if I introduce a sleep between calls when the first call includes the "If-Modified-Since" header field the first call will return 304 correctly and then after the sleeps the remaining calls will also execute and return correctly. It appears that something in NSURLConnection is caching the connection or response and then returning them without even submitting the request. I've attached a project that will allow you to see all 3 of these states. I'm also including some pictures of the HTTP scoop results beside the iPhone simulator running the test app.


Please note: Reports posted here will not necessarily be seen by Apple. All problems should be submitted at bugreport.apple.com before they are posted here. Please only post information for Radars that you have filed yourself, and please do not include Apple confidential information in your posts. Thank you!