Can WinInet HttpQueryInfo return raw bytes? (HTTP

2019-07-22 19:34发布

The built-in routine HttpQueryInfo returns a string, not actual bytes. Normally that is not a problem.

However, lately I have begin to encounter a problem with servers issuing redirects where the location header field contains an URL which includes non-percentage-encoded unicode/or? characters. Any way around this?

        var
          vContent_Wide: WideString;
        begin 
          vBufferSize := 4096;
          GetMem(vBufferPtr, vBufferSize);
          while True do
          begin
            TmpFakeCardinal := 0;
            vErrorNone := HttpQueryInfo(
              hHttpOpen_Request,
              HTTP_QUERY_RAW_HEADERS_CRLF,
              vBufferPtr,
              vBufferSize,
              TmpFakeCardinal
            );
            if (vErrorNone = False) then
              begin
                vErrorID := GetLastError;
                if (vErrorID = ERROR_INSUFFICIENT_BUFFER) then
                  begin
                    FreeMem(vBufferPtr);
                    GetMem(vBufferPtr, vBufferSize);
                  end
                else Break;
              end
            else
              begin
                vContent_Wide := PWideChar(vBufferPtr); 
                Result := vContent_Wide;
                Break;
              end
            ;
          end;
          FreeMem(vBufferPtr, vBufferSize);

1条回答
\"骚年 ilove
2楼-- · 2019-07-22 20:01

URIs do not support unencoded Unicode characters. If the server is sending a non-percent-encoded Unicode string in the Location header then the server is buggy and needs to be fixed as this is a clear violation of RFC 2616 section 14.30. My guess is that the server is actually sending an unmapped IRI (RFC 3987) instead of a URI (RFC 3986). HTTP does not support direct use of IRIs, they have to be mapped to URIs (RFC 3987 defines how to do that).

With that said, check if setting the dwInfoLevel parameter to HTTP_QUERY_CUSTOM allows HttpQueryInfo() to return the raw bytes of the header or not. If not, then you will not be able to use WinInet for those servers that are failing, as there are no other functions in the WinInet API that can access HTTP headers. You will have to find another HTTP library that supports what you need, or else you can drop down to the TCP/IP layer and implement the HTTP protocol manually in your own code.

查看更多
登录 后发表回答