纯vc sdk实现http post 方式上传数据到web服务器

刚开始的时候想google一个合适的代码.但是非常失望,可能我的搜索技巧不够好,找到的几个代码都是存在这样或那样的问题

要么就是MFC实现,总之是不能满足自己的要求,所以在找了n多代码浪费了大量时间的情况下 还是自己写吧  这样的程序没什么

太大的意思,写一次以后拷贝着用就可以了 所以贴这里备用吧

 

流程:

       1:获得文件内容

       2:构造http头备用

       3:构造http尾备用

       4:与http建立连接

       5:发送...

       6:提交

 

要点:

      1:http头的构造


[cpp]  view plain  copy
  1. // upload.cpp : Defines the entry point for the console application.    
  2. #include "stdafx.h"    
  3. #include <windows.h>    
  4. #include <string>    
  5. #include <stdlib.h>    
  6. #include <Wininet.h>    
  7. #include <TCHAR.H>    
  8. using namespace std ;    
  9. #pragma comment(lib,"Wininet.lib")      
  10. string MakeRequestHeaders(string &strBoundary)    
  11. {    
  12.     string strData;    
  13.         
  14.     strData += _T("Content-Type: multipart/form-data; boundary=");    //二进制文件传送Content-Type类型为: multipart/form-data    
  15.     strData += strBoundary;    
  16.     strData +="/r/n";    
  17.     return strData;    
  18. }    
  19. string MakePreFileData(string &strBoundary, string &strFileName, int iRecordID)    
  20. {    
  21.     //    
  22.     string strData;    
  23.         
  24.     strData += _T("--");    
  25.     strData += strBoundary;    
  26.     strData += _T("/r/n");    
  27.     strData += _T("Content-Disposition: form-data; name=/"file1/"; filename=/"");  //必备1:Path    
  28.     strData += strFileName;                                             
  29.     strData += _T("/"");    
  30.     strData += _T("/r/n");    
  31.     strData += _T("Content-Type: image/pjpeg");                                     //必备2:Type    
  32.         
  33.     strData += _T("/r/n/r/n");    
  34.         
  35.     return strData;    
  36. }    
  37. string MakePostFileData(string &strBoundary)    
  38. {    
  39.     string strData;    
  40.         
  41.     strData = _T("/r/n");       
  42.     strData += _T("--");    
  43.     strData += strBoundary;    
  44.     strData += _T("/r/n");    
  45.     strData += _T("Content-Disposition: form-data; name=/"submitted/"");    
  46.     strData += _T("/r/n/r/n");    
  47.     strData += _T("hello");    
  48.     strData += _T("/r/n");    
  49.     strData += _T("--");    
  50.     strData += strBoundary;    
  51.     strData += _T("--");    
  52.     strData += _T("/r/n");    
  53.     return strData;    
  54. }    
  55. //文件长度与文件内容     
  56. typedef struct _FileInfo    
  57. {    
  58.     DWORD  nFileLen;    
  59.     DWORD  nFileHighLen;                
  60.     LPSTR FileBuf;    
  61. }FileInfo,*pFileInfo;    
  62. BOOL GetFileInfo(OUT FileInfo &BinaryInfo, IN string FilePath)    
  63. {    
  64.     BOOL   nRet = FALSE;    
  65.     HANDLE hFile;     
  66.     DWORD nBytesRead;    
  67.     hFile = CreateFile(FilePath.c_str(),              
  68.         GENERIC_ALL,              // open for reading     
  69.         FILE_SHARE_READ,           // share for reading     
  70.         NULL,                      // no security     
  71.         OPEN_EXISTING,             // existing file only     
  72.         FILE_ATTRIBUTE_NORMAL,     // normal file     
  73.         NULL);                     // no attr. template %    
  74.         
  75.     if (hFile == INVALID_HANDLE_VALUE)     
  76.     {     
  77.         return nRet;    
  78.     }     
  79.         
  80.     BinaryInfo.nFileLen = GetFileSize(hFile,&BinaryInfo.nFileHighLen);    
  81.     BinaryInfo.FileBuf = new char[BinaryInfo.nFileLen];    
  82.     if (!BinaryInfo.FileBuf)    
  83.     {    
  84.         CloseHandle(hFile);    
  85.         return nRet;    
  86.     }    
  87.     ZeroMemory(BinaryInfo.FileBuf,BinaryInfo.nFileLen);    
  88.     if (!ReadFile(hFile, BinaryInfo.FileBuf, BinaryInfo.nFileLen, &nBytesRead, NULL))    
  89.     {    
  90.         CloseHandle(hFile);    
  91.         return nRet;    
  92.     }    
  93.         
  94.     CloseHandle(hFile);    
  95.     nRet = TRUE;    
  96.     return nRet;    
  97. }    
  98. /*  
  99.  * 本地路径 服务器地址 服务器路径 数据分割信息 端口  
  100.  * 通过以上传入信息 将二进制数据传入web服务器  
  101.  *  
  102. */    
  103. BOOL Upload(IN string& FilePath,IN string& ServerName,IN string& ObjectName, IN string& HTTPBoundary,IN INTERNET_PORT &nPort)    
  104. {    
  105.     BOOL      nRet = FALSE;    
  106.     HINTERNET hInternet;                //by   InternetOpen    
  107.     HINTERNET hHttpSession;             //by   InternetConnect    
  108.     HINTERNET hHttpRequest;             //by   HttpOpenRequest    
  109.     int       iRecordID = 1;    
  110.     DWORD     dwTotalLen;               //数据包的总长度    
  111.     //准备工作    
  112.     int    startp   = FilePath.find('//');    
  113.     int    namelen  = FilePath.length()-startp-1;    
  114.     string FileName = FilePath;    
  115.         
  116.     string strHeaders   = MakeRequestHeaders(HTTPBoundary);    
  117.     string PreFileData  = MakePreFileData(HTTPBoundary, FileName, iRecordID);    
  118.     string PostFileData = MakePostFileData(HTTPBoundary);    
  119.     //    
  120.     //1:getFileInfo    
  121.     FileInfo localJpg;    
  122.     if (!GetFileInfo(localJpg,FilePath))    
  123.     {    
  124.         return FALSE;    
  125.     }    
  126.     dwTotalLen = localJpg.nFileLen + PreFileData.length() + PostFileData.length();    
  127.     //2:init www    
  128.     hInternet = InternetOpen(_T("lpszAgent"),    
  129.                              INTERNET_OPEN_TYPE_DIRECT,     
  130.                              NULL,    
  131.                              NULL,    
  132.                              0);    
  133.         
  134.     if (!hInternet)    
  135.     {    
  136.         return nRet;    
  137.     }    
  138.         
  139.     hHttpSession = InternetConnect( hInternet,    
  140.                                     ServerName.c_str(),    
  141.                                     INTERNET_DEFAULT_HTTP_PORT,    
  142.                                     NULL,    
  143.                                     NULL,    
  144.                                     INTERNET_SERVICE_HTTP,    
  145.                                     INTERNET_FLAG_RELOAD,0);         
  146.         
  147.     if (hHttpSession == NULL)    
  148.     {    
  149.             
  150.         InternetCloseHandle(hInternet);    
  151.         return nRet;    
  152.     }    
  153.     //3:Opening a Request    
  154.     hHttpRequest = HttpOpenRequest(hHttpSession, _T("POST"),     
  155.                                    ObjectName.c_str(),    
  156.                                    HTTP_VERSIONA,     
  157.                                    NULL,NULL, INTERNET_FLAG_MAKE_PERSISTENT,1);     
  158.     if (hInternet == NULL)    
  159.     {    
  160.         InternetCloseHandle(hHttpSession);    
  161.         InternetCloseHandle(hInternet);    
  162.         return nRet;    
  163.     }    
  164.     //4:HttpAddRequestHeaders    
  165.     if (!HttpAddRequestHeaders(hHttpRequest,strHeaders.c_str(),strHeaders.length(),HTTP_ADDREQ_FLAG_ADD))    
  166.     {       
  167.         goto END;    
  168.     }    
  169.         
  170.     //5:HttpSendRequestEx    
  171.     INTERNET_BUFFERSA buffer;    
  172.     memset(&buffer, 0, sizeof(buffer));    
  173.     buffer.dwStructSize  = sizeof(buffer);    
  174.     buffer.dwBufferTotal = dwTotalLen;    
  175.     if (!HttpSendRequestEx(hHttpRequest,&buffer,NULL,HSR_SYNC | HSR_INITIATE,1))    
  176.     {    
  177.         goto END;    
  178.     }    
  179.         
  180.     //6:_A_send http头    
  181.     DWORD dwNumberOfBytesWritten;       
  182.     if(!InternetWriteFile(hHttpRequest,PreFileData.c_str(),PreFileData.length(),&dwNumberOfBytesWritten))    
  183.     {    
  184.         goto END;    
  185.     }    
  186.     if (dwNumberOfBytesWritten != PreFileData.length())    
  187.     {    
  188.         goto END;    
  189.     }    
  190.         
  191.     //6:_B_send filedata    
  192.     if(!InternetWriteFile(hHttpRequest,localJpg.FileBuf,localJpg.nFileLen,&dwNumberOfBytesWritten))    
  193.     {    
  194.         goto END;    
  195.     }    
  196.         
  197.     if (dwNumberOfBytesWritten != localJpg.nFileLen)    
  198.     {    
  199.         goto END;    
  200.     }    
  201.     //6:_C_send Http尾    
  202.     if(!InternetWriteFile(hHttpRequest,PostFileData.c_str(),PostFileData.length(),&dwNumberOfBytesWritten))    
  203.     {    
  204.         goto END;    
  205.     }    
  206.         
  207.     if (dwNumberOfBytesWritten != PostFileData.length())    
  208.     {    
  209.         goto END;    
  210.     }    
  211.     //7:完成提交 必不可少    
  212.     HttpEndRequest(hHttpRequest,NULL,HSR_SYNC,1);    
  213. END:    
  214.     InternetCloseHandle(hHttpRequest);    
  215.     InternetCloseHandle(hHttpSession);    
  216.     InternetCloseHandle(hInternet);    
  217.     return nRet;    
  218. }    
  219. int main(int argc, char* argv[])    
  220. {    
  221.     string          FilePath     = _T("C://test//16.jpg");;                             //本地文件路径    
  222.     string          ServerName   = _T("www.baidu.com");                                 //服务器地址    
  223.     string          ObjectName   = _T("//test//upload//upload.asp");                    //服务器文件对象    
  224.     string          HTTPBoundary = _T("---------------------------7db29f2140360");      //边界值:要求不严格    
  225.     INTERNET_PORT   nPort        = 80;                                                  //端口    
  226.     Upload(FilePath,ServerName,ObjectName,HTTPBoundary,nPort);    
  227.     return 0;    
  228. }    

补充:在实验过程中,在服务器要求不严格的情况下,buffer的内容可以自定义,而不一定需要完全符合jpg...的格式,但是

Content-Disposition: form-data; name=/"file1/"; filename=/"jj.yy'")这个地方filename的后缀必须是jpg格式



http://blog.csdn.net/chinafe/article/details/14643607

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值