C++Builder Programming Forum
C++Builder  |  Delphi  |  FireMonkey  |  C/C++  |  Free Pascal  |  Firebird
볼랜드포럼 BorlandForum
 경고! 게시물 작성자의 사전 허락없는 메일주소 추출행위 절대 금지
C++빌더 포럼
Q & A
FAQ
팁&트릭
강좌/문서
자료실
컴포넌트/라이브러리
메신저 프로젝트
볼랜드포럼 홈
헤드라인 뉴스
IT 뉴스
공지사항
자유게시판
해피 브레이크
공동 프로젝트
구인/구직
회원 장터
건의사항
운영진 게시판
회원 메뉴
북마크
볼랜드포럼 광고 모집

C++빌더 Q&A
C++Builder Programming Q&A
[22055] [만해] WinInet을 이용한 객체 자료를 받아 들이는 루틴인데요 좀 봐주세요
만해 [greenuri] 2904 읽음    2002-10-16 05:59
안녕하세요 만해입니다.

지금 만드는 프로그램에서 쓰이는 루틴인데요

어떤 거냐면요

팁&트릭에 있는 임프님의 소스를 약간 고쳐서 만든

웹 페이지에 있는 그림 파일이나 미디어 파일 같은 그런 파일의

용량, 상태 코드, 파일의 종류를 받아 오는 루틴인데요

이게 딜레이가 너무 많이 걸리네요

좀더 빨리 할수 있는 방법이 없을까요?

아시는분 좀 알려 주세요

우선은 전체 소스를 올립니다.


TContent_Struct __fastcall TFrmSiteExplorer::GetObjData(AnsiString StrUrl)
{
  TContent_Struct ObjData;
  ObjData.AContent_Size = 0;
  ObjData.AStatus_Code  = 0;
  ObjData.AContent_Type = "";
  if ( StrUrl.AnsiPos("http://") <= 0 )
   StrUrl = "http://" + StrUrl;

  AnsiString Agent = "Mozilla/4.0+(compatible;+MSIE+6.0;+Windows+NT+5.0)";
  HINTERNET ISession = InternetOpen(Agent.c_str() , INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0);
  HINTERNET HttpFile = InternetOpenUrl(ISession, StrUrl.c_str(), NULL, 0, INTERNET_FLAG_DONT_CACHE, 0);

  AnsiString UrlBuff;
  UrlBuff.SetLength(1024);
  DWord BuffSize = 1024;
  AnsiString Status_Code;
  Status_Code.SetLength(32);
// Content Status Code을 받아 내는 부분
  if(HttpQueryInfo(HttpFile, HTTP_QUERY_STATUS_CODE, Status_Code.c_str(), &BuffSize, NULL)==false)
  {
    switch(GetLastError())
     {
       case ERROR_INSUFFICIENT_BUFFER:
       Status_Code.SetLength(Status_Code.Length()+1);
       HttpQueryInfo(HttpFile, HTTP_QUERY_STATUS_CODE, Status_Code.c_str(), &BuffSize, 0);
       break;

       case ERROR_HTTP_HEADER_NOT_FOUND:
       Status_Code = "";
       break;

       default:
       InternetCloseHandle(HttpFile);
     }
  }
  ObjData.AStatus_Code = Status_Code.ToIntDef(404);

  if ( ObjData.AStatus_Code == 404 )
    {
      ObjData.AContent_Size = -1;
      ObjData.AContent_Type = "Not Found";
      return ObjData;
    }

  if(HttpQueryInfo(HttpFile, HTTP_QUERY_CONTENT_LOCATION, UrlBuff.c_str(), &BuffSize, NULL)==false)
  {
       switch(GetLastError())
       {
             case ERROR_INSUFFICIENT_BUFFER:
             UrlBuff.SetLength(BuffSize+1);
             HttpQueryInfo(HttpFile, HTTP_QUERY_CONTENT_LOCATION, UrlBuff.c_str(), &BuffSize, 0);
             break;

             case ERROR_HTTP_HEADER_NOT_FOUND:
             UrlBuff = StrUrl;
             break;

             default:
             InternetCloseHandle(HttpFile);
       }
  }

  char FileSizeBuff[4];
  BuffSize = sizeof(FileSizeBuff);

// Content Size를 받아 내는 부분
  bool bSizeIsKnown = HttpQueryInfo(HttpFile, HTTP_QUERY_CONTENT_LENGTH, &FileSizeBuff, &BuffSize, NULL);
  bool Result;
  DWord FileSize;
  if(bSizeIsKnown)
  {
       FileSize = atol(FileSizeBuff);
       ObjData.AContent_Size = FileSize;
  }
  else
  {
       char *Buffer = new char[2048];
       FileSize = 2048;
       unsigned long ByteRead;
       unsigned long Count = 1000;
       while(true)
       {
         Count--; //이 부분에서 무한 루프가 걸려서 일부러 카운터로 무한루프를 방지
         Sleep(1);// 그런데 자주 무한 루프로 빠지네요 흑흑~
         Application->ProcessMessages();
         Result = InternetReadFile(HttpFile, Buffer, FileSize, &ByteRead);
         ObjData.AContent_Size += ByteRead;
         if ( ByteRead==0 )
           break;
         if ( Count == 0 )
          {
            ObjData.AContent_Size = -1;
            break;
          }

       }
       delete[] Buffer;
  }

  AnsiString  Content_Type;
  Content_Type.SetLength(32);
// Content Type을 받아 내는 부분
  if(HttpQueryInfo(HttpFile, HTTP_QUERY_CONTENT_TYPE , Content_Type.c_str(), &BuffSize, NULL)==false)
  {
    switch(GetLastError())
     {
       case ERROR_INSUFFICIENT_BUFFER:
       Content_Type.SetLength(BuffSize+1);
       HttpQueryInfo(HttpFile, HTTP_QUERY_CONTENT_TYPE, Content_Type.c_str(), &BuffSize, 0);
       break;

       case ERROR_HTTP_HEADER_NOT_FOUND:
       UrlBuff = "";
       break;

       default:
       InternetCloseHandle(HttpFile);
     }
  }
  ObjData.AContent_Type.assign(Content_Type.c_str());

  InternetCloseHandle(HttpFile);
  InternetCloseHandle(ISession);

  return ObjData;
}

여기까지가 소스 입니다.

이보다 좋은 소스나 혹은

소스 상의 오류가 있음 알려 주세요

부탁 드릴께요

이 소스를

데브피아에서 찾은

CInternetSession mysession("mysession");
mysession.SetCookie(m_szSessionURL, "JSESSIONID", (LPCTSTR)m_szSessionID );

CHttpFile *remotefile =
(CHttpFile*)mysession.OpenURL((LPCTSTR)m_szUrls,1,INTERNET_FLAG_TRANSFER_BINARY);

TCHAR szContentLength[100];
DWORD dwInfoSize = 32;
DWORD dwFileSize = 0;

// 이부분에서 서버로 리퀘스트를 한번 더 보내주시면 됩니다.
CString Header;
Header.Format("Range: bytes=0-\r\n");
remotefile->SendRequest(Header);
// 0바이트부터 받아오라는 메세지를 그냥 보냅니다-_-;

if (remotefile->QueryInfo( HTTP_QUERY_CONTENT_LENGTH, szContentLength, &dwInfoSize , NULL))
{
::MessageBox(NULL, szContentLength, "", MB_OK | MB_SETFOREGROUND);
}
else
{
::MessageBox(NULL, "Can't Query!", "", MB_OK | MB_SETFOREGROUND);
}

이 소스처럼 되어야 하는데

CHttpFile구조가 빌더에서 뭔지 모르겠네요

혹 아시는분 좀 갈켜 주세요~

+ -

관련 글 리스트
22055 [만해] WinInet을 이용한 객체 자료를 받아 들이는 루틴인데요 좀 봐주세요 만해 2904 2002/10/16
Google
Copyright © 1999-2015, borlandforum.com. All right reserved.