无法从Web服务器读取UTF-8缓冲区

cannot read utf-8 buffer from web server

本文关键字:读取 UTF-8 缓冲区 服务器 Web      更新时间:2023-10-16

我正在写一个带有C 的简单Web爬虫。

它连接到Web服务器并发送" GET"请求,然后从Web服务器接收回复。

这是我用来执行此操作的代码:

CHttpHeader reqHeader = websock.GenerateRequestHeader(url, nullptr);
dwResponse = websock.SendRequest(url, reqHeader, nullptr, nullptr);
if (dwResponse == 0)    {
    //::MessageBoxA(this->GetSafeHwnd(), "error to send http request", 0, 0);
    return;
}
//char*strstr = "병맛메로나";
//  Receive Response
const int bufferSize = 1024 * 1024 * 1;
char * buffer = new char[bufferSize * 10];
char *tbuffer = new char[bufferSize];
int recvLen = 0;
DWORD dwNextOffset = 0;

//setlocale(LC_ALL, "");
while (websock.HasMoreResponse())   {
    recvLen = websock.Recv(tbuffer, bufferSize);
    ::memcpy(buffer + dwNextOffset, tbuffer, recvLen);
    dwNextOffset+= recvLen;
}

服务器回复将复制到buffer长度。

的CC_1中。

每件事都可以连接到服务器并正确接收回复。但是,在某些情况下,使用UTF-8编码答复,我无法从缓冲区读取HTML标签。它全部gibberish。

我想这是由于客户端/服务器操作系统的差异。因为我在Windows上以及Web服务器是IIS时,很可能在Windows上运行,所以读取UTF-8编码字符没有问题。但是,在某些情况下,此问题发生了。

utf-8格式在OS之间是否不同?

如果是这样,我可以正确转换为MBC吗?


编辑:这是文件保存部分:

FILE* fp = nullptr;
::fopen_s(&fp, "result", "wb");
::fwrite(buffer, 1, dwOffset, fp);
::fclose(fp);

结果是..

http/1.1 200好日期:2018年2月27日星期二12:19:19格林尼治标准时间X-UA兼容:IE = 10到期:1970年1月1日星期六22:00:00 GMTPRAGMA:无搜索缓存控制:无缓存,无存储,必须重视P3P:CP ="所有DSP Cor Mon Law Ivdi他的Ivai Deli Sami我们的腿Phy Uni onl dem dem dem sta int nav pur fin fin otc gov"内容类型:text/html; charset = utf-8内容语言:ko-kr不同:接受编码内容编码:GZIPX-UA设备类型:PC内容长度:49043连接:关闭?酱??/影?? -  〜퍏뙗*쿭돃?긥먉^...

编辑:Max Vollmer,您是对的。在请求中使用Accept-Encoding : identity解决了一些问题。但是还有另一个问题。

如果我使用此代码:

char *strstr = "병맛메로나";
std::string tstr(strstr);

tstr工作正常。

但是,如果我将buffer放入std::string中,它将再次具有Gibberish。

std::string tstr(buffer);

为什么会发生这种情况?

您的第一个问题,压缩:

Content-Encoding: gzip

您的数据被压缩,您必须对其进行解压缩。参见内容编码。有很多C 库可以这样做。

另外,您可以随请求发送Accept-Encoding: identity标头,因此服务器不会发送压缩数据。参见接受编码。

您的第二个问题,编码:

如果Buffer是UTF-8编码,则不能仅做std::string tstr(buffer);。首先,这根本不会解码任何UTF-8字符。您甚至都不知道您的数据是UTF-8编码的,该怎么知道?其次,任何需要超过8个字节的字符均无法由单个char表示,并且STD :: String使用char为其字符,因此std::string永远无法保存UTF-8编码数据的文本表示。

您可能会对char实际是什么感到困惑。这是一个具有8位大小的整数。

由于UTF-8编码具有多个字节的特殊字符,因此这些字符将存储在您的字符数组中的多个字符中。当您只用该char数组创建一个std::string时,它将仅将每个字符解释为一个字符,这是错误的。

您必须将UTF-8数据解码为多键字符串,例如std::wstring,或使用一些提供一些支持UTF-8的字符串类的第三方库。或者只需将数据写入文件,然后用支持UTF-8的文本编辑器打开该文件,它应该自动检测编码。确实取决于您要做什么。

这是一种将UTF-8编码数据转换为std::wstring的简单方法:

std::wstring_convert<std::codecvt_utf8<wchar_t>> converter;
std::wstring text = converter.from_bytes(buffer);