Click for example
所有utf8字符都没有正确编纂.
这是我的访问例程:
var Web : TIdHTTP; Sito : String; hIOHand : TIdSSLIOHandlerSocketOpenSSL; begin Url := TIdURI.URLEncode(Url); try Web := TIdHTTP.Create(nil); hIOHand := TIdSSLIOHandlerSocketOpenSSL.Create(nil); hIOHand.DefStringEncoding := IndyTextEncoding_UTF8; hIOHand.SSLOptions.SSLVersions := [sslvTLSv1,sslvTLSv1_1,sslvTLSv1_2,sslvSSLv2,sslvSSLv3,sslvSSLv23]; Web.IOHandler := hIOHand; Web.Request.CharSet := 'utf-8'; Web.Request.UserAgent := INET_USERAGENT; //Custom user agent string Web.RedirectMaximum := INET_REDIRECT_MAX; //Maximum redirects Web.HandleRedirects := INET_REDIRECT_MAX <> 0; //Handle redirects Web.ReadTimeOut := INET_TIMEOUT_SECS * 1000; //Read timeout msec try Sito := Web.Get(Url); Web.Disconnect; except on e : exception do Sito := 'ERR: ' +Url+#32+e.Message; end; finally Web.Free; hIOHand.Free; end;
我尝试了所有的解决方案,但在Sito var我发现错误的characthers,例如“名称”的正确值
“名称”:“A dd’adhésionduParc national du Mercantour”,
但在获得Get指令之后
“名称”:“Aire d’adhéithionParc national du Mercantour”,
你知道我的错误在哪里吗?
谢谢你们!
您正在使用返回字符串的TIdHTTP.Get()的重载版本.它使用响应报告的任何字符集将发送的文本解码为UTF-16.如果文本未正确解码,则可能意味着响应未报告正确的字符集.如果使用了错误的字符集,则文本将无法正确解码.
实际上,有问题的URL是发送一个响应Content-Type标头,该标头设置为application / json而根本没有指定字符集. application / json的默认字符集是UTF-8,但Indy不知道,所以它最终使用自己的内部默认值,而不是UTF-8.这就是当存在非ASCII字符时文本无法正确解码的原因.
在这种情况下,如果您知道字符集将始终为UTF-8,您可以选择以下几种解决方法:
>您可以通过在IdGlobal单元中设置全局GIdDefaultTextEncoding变量,将Indy的默认字符集设置为UTF-8:
GIdDefaultTextEncoding := encUTF8;
>如果它是空白或不正确,您可以使用TIdHTTP.OnHeadersAvailable事件将TIdHTTP.Response.Charset属性更改为’utf-8′.
Web.OnHeadersAvailable := CheckResponseCharset; ... procedure TMyClass.CheckResponseCharset(Sender: TObject; AHeaders: TIdHeaderList; var VContinue: Boolean); var Response: TIdHTTPResponse; begin Response := TIdHTTP(Sender).Response; if IsHeaderMediaType(Response.ContentType, 'application/json') and (Response.Charset = '') then Response.Charset := 'utf-8'; VContinue := True; end;
>您可以使用填充输出TStream而不是返回字符串的TIdHTTP.Get()的其他重载版本.使用TMemoryStream或TStringStream,您可以使用UTF-8自己解码原始字节:
MStrm := TMemoryStream.Create; try Web.Get(Url, MStrm); MStrm.Position := 0; Sito := ReadStringFromStream(MStrm, IndyTextEncoding_UTF8); finally SStrm.Free; end;
SStrm := TStringStream.Create('', TEncoding.UTF8); try Web.Get(Url, SStrm); Sito := SStrm.DataString; finally SStrm.Free; end;