2011-07-09 20 views
3

我试图从使用WinINet库调用的http服务器下载文件。它在我的本地Web服务器上工作得很好。但是当我试图从互联网上下载东西时,InternetReadFile只读取任何文件(文本或二进制文件)〜10kb。在下面的例子中TRANSFER_SIZE = 4096,因此有两个读取4kb和一个2kb。每下一个InternetReadFile返回true并读取0个字节。InternetReadFile只读10kb

hInternet = InternetOpen(L"Agent", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 
    DWORD options = INTERNET_FLAG_NEED_FILE|INTERNET_FLAG_HYPERLINK|INTERNET_FLAG_RESYNCHRONIZE|INTERNET_FLAG_RELOAD; 
    HINTERNET hSession = InternetOpenUrl(hInternet, URL, NULL, NULL, options, 0); 

    hFile = CreateFile(...); 
    ... 
    do { 
     DWORD dwWriteSize, dwNumWritten; 
     BOOL bRead = InternetReadFile(hSession, pBuf, TRANSFER_SIZE, &dwReadSizeOut); 
     dwWriteSize = dwReadSizeOut; 

     if (bRead && dwReadSizeOut > 0) { 
      dwTotalReadSize += dwReadSizeOut; 
      WriteFile(hFile, pBuf, dwWriteSize, &dwNumWritten, NULL); 
      // File write error 
      if (dwWriteSize != dwNumWritten) { 
       CloseHandle(hFile);      
       return false; 
      } 
     } 
     else { 
      if (!bRead) 
      { 
       // Error 
       CloseHandle(hFile);  
       return false; 
      }   
      break; 
     } 
    } while(1); 

如何使用WinINet库下载整个文件?

+2

您是否运行过数据包嗅探器(NetMon,wiresark等)来检测提供该URL的Web服务器是否实际上向您发送了您期望的字节? – selbie

+0

我的意思是“wireshark”。即使是“小提琴手”也是有用的。 – selbie

+1

InternetReadFile应该像在本地网络服务器上那样运行在Internet上。某处发生了某些变化;如果它不是你的代码,那么扩展你的故障排除。仔细检查网络服务器的响应是否是您期望的,并且中间没有其他硬件或软件导致此行为。看到这个问题的一个惊人的结果类似的问题的一个很好的例子:http://stackoverflow.com/questions/5771636/internetopenurl-only-returns-after-entire-http-response-is-downloaded/5772571 –

回答

0

我读的响应文本和它是“404错误”从Web服务器响应 - 文件不见了。所以它是有用的阅读回应;)

和libcurl看起来像WinINet库很好的替代品 - 更容易开始,很多选择。

2

尝试在InternetOpenURl上设置INTERNET_FLAG_KEEP_CONNECTION。

打开后,您还应该在句柄上至少执行HttpQueryInfo(HTTP_QUERY_STATUS_CODE | HTTP_QUERY_FLAG_NUMBER)。

我建议寻找一些现有的封装C++类这些东西, http://www.google.com/codesearch#search/&q=INTERNET_FLAG_KEEP_CONNECTION%20lang:c%2B%2B&type=cs

+0

谢谢!看起来好像我没有自己编写一堆代码,我不会花那么多时间在那里寻找错误。 我还被建议下次使用libcurl - 看起来很好,许可证也可以。 – polotenchiko

+0

非常感谢您提及INTERNET_FLAG_KEEP_CONNECTION – gdy