Note that there are some explanatory texts on larger screens.

plurals
  1. POHttpSendRequest not getting latest file from server
    primarykey
    data
    text
    <p>I am having an issue with my HTTP requests in my app, such that if the remote file is the same size as the local file (even though its modified time is different, as its contents have been changed), attempts to download it return quickly and the newer file is not downloaded.</p> <p>In short, the process I am following is: Setting up an HTTP connection with the <code>INTERNET_FLAG_RESYNCHRONIZE</code> flag and calling HttpSendRequest(); then checking the HTTP status code and finding it to be "200".</p> <ul> <li><b>If the remote file is updated, but remains the same size as the local copy</b>: The local file is unchanged after running the app. If I call <code>HttpQueryInfo()</code> with <code>HTTP_QUERY_LAST_MODIFIED</code> after sending the request, it gives me the actual last modified time of the server's file, which I can see is different from the local file I am trying to have it overwrite.</li> <li><b>If the remote file is updated, and the file size becomes different from the local copy</b>: It is downloaded and overwrites the local copy as expected.</li> </ul> <p>Here's a fairly abridged version of the code, to cut out helpers and error checking:</p> <pre><code>// szAppName = our app name HINTERNET hInternetHandle = InternetOpen( szAppName, INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0 ); // szServerName = our server name hInternetHandle = InternetConnect( hInternetHandle, szServerName, INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, INTERNET_SERVICE_HTTP, NULL, 0 ); // szPath = the file to download LPCSTR aszDefault[2] = { "*/*", NULL }; DWORD dwFlags = 0 | INTERNET_FLAG_IGNORE_REDIRECT_TO_HTTP | INTERNET_FLAG_IGNORE_REDIRECT_TO_HTTPS | INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_NO_AUTH | INTERNET_FLAG_NO_AUTO_REDIRECT | INTERNET_FLAG_NO_COOKIES | INTERNET_FLAG_NO_UI | INTERNET_FLAG_RESYNCHRONIZE; HINTERNET hHandle = HttpOpenRequest( hInternetHandle, "GET", szPath, NULL, NULL, aszDefault, dwFlags, 0 ); DWORD dwTimeOut = 10 * 1000; // In milliseconds InternetSetOption( hInternetHandle, INTERNET_OPTION_CONNECT_TIMEOUT, &amp;dwTimeOut, sizeof( dwTimeOut ) ); InternetSetOption( hInternetHandle, INTERNET_OPTION_RECEIVE_TIMEOUT, &amp;dwTimeOut, sizeof( dwTimeOut ) ); InternetSetOption( hInternetHandle, INTERNET_OPTION_SEND_TIMEOUT, &amp;dwTimeOut, sizeof( dwTimeOut ) ); DWORD dwRetries = 5; InternetSetOption( hInternetHandle, INTERNET_OPTION_CONNECT_RETRIES, &amp;dwRetries, sizeof( dwRetries ) ); HttpSendRequest( hInternetHandle, NULL, 0, NULL, 0 ); </code></pre> <p>Since I have found I can query the remote file's last modified time, and find it to be accurate, I know it's actually getting to the server. I thought that specifying <code>INTERNET_FLAG_RESYNCHRONIZE</code> would force the file to <a href="http://msdn.microsoft.com/en-us/library/aa918422.aspx" rel="nofollow noreferrer">resynch if it's out of date</a>. Do I have it all wrong? Is this just how it's supposed to work?</p> <hr> <p>Edit: I've done some investigation with a packet sniffer, and here's some additional information:</p> <p>If the remote and local file are exactly the same, this is the exchange:</p> <pre><code>GET /test.bmp HTTP/1.1 Accept: */* If-None-Match: "1c1467112ee6ca1:369" User-Agent: Internal Testing Host: **************** Connection: Keep-Alive HTTP/1.1 304 Not Modified Last-Modified: Tue, 27 Apr 2010 17:21:26 GMT Accept-Ranges: bytes ETag: "1c1467112ee6ca1:369" Server: Microsoft-IIS/6.0 X-Powered-By: ASP.NET Date: Tue, 27 Apr 2010 18:10:26 GMT </code></pre> <p>Now, if the remote file has changed, but remains the same file size:</p> <pre><code>GET /test.bmp HTTP/1.1 Accept: */* If-None-Match: "1c1467112ee6ca1:369" User-Agent: Internal Testing Host: **************** Connection: Keep-Alive HTTP/1.1 200 OK Content-Length: 419958 Content-Type: image/bmp Last-Modified: Tue, 27 Apr 2010 18:11:17 GMT Accept-Ranges: bytes ETag: "b65425835e6ca1:369" Server: Microsoft-IIS/6.0 X-Powered-By: ASP.NET Date: Tue, 27 Apr 2010 18:11:33 GMT [Block of data] </code></pre> <p>So, the server is indeed sending the file when it has changed, but my app still seems to see it as not having changed. I am thinking the problem lies in how my app is dealing with the response; it's not my own code, and the guy who wrote it has moved on long ago.</p> <p>One problem I've found is that in <em>both</em> of the above scenarios, when I call <code>HttpQueryInfo()</code> with <code>HTTP_QUERY_STATUS_CODE</code> I get 200 back. However, in the first case above I can see that the actual server response was 304, not 200. Digging into the code we're using, I found that it seems to be trying to work around this by doing a filesize comparison, and assuming the file hasn't changed if the filesizes are the same; hence, the problem I am having!</p> <p>So now my question is more simply: why would <code>HttpQueryInfo()</code> return 200 even when the server is returning one of the 3XX errors? I've found some people asking a similar question online, but they either <a href="http://forums.devx.com/showthread.php?t=156401" rel="nofollow noreferrer">received no responses</a> or were dealing with web browsers directly.</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload