使用套接字从页面加载数据
load data from page with socket
我选择不使用libcurl,因为我已经花了太多的精力来尝试让它工作
所以我对c++还不是很熟悉,并不是什么都懂。
我无法从example.com/test.php中获取内容,但使用test.example.com确实有效(但不得不为其创建子域,这很烦人)
除此之外,有没有一种方法可以只获取内容而不获取响应标头?
我的代码:
string result;
WSADATA wsaData;
if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) {
cout << "WSAStartup failed.n";
system("pause");
}
SOCKET Socket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
struct hostent *host;
host = gethostbyname("www.example.com");
SOCKADDR_IN SockAddr;
SockAddr.sin_port = htons(80);
SockAddr.sin_family = AF_INET;
SockAddr.sin_addr.s_addr = *((unsigned long*)host->h_addr);
cout << "Connecting...n";
if (connect(Socket, (SOCKADDR*)(&SockAddr), sizeof(SockAddr)) != 0){
cout << "Could not connect";
system("pause");
}
cout << "Connected.n";
send(Socket, "GET / HTTP/1.1rnHost: test.example.nlrnConnection: closernrn", strlen("GET / HTTP/1.1rnHost: test.example.nlrnConnection: closernrn"), 0);
char buffer[10000];
int nDataLength;
while ((nDataLength = recv(Socket, buffer, 10000, 0)) > 0){
int i = 0;
while (buffer[i] >= 32 || buffer[i] == 'n' || buffer[i] == 'r') {
result += buffer[i];
i += 1;
}
}
cout << result;
closesocket(Socket);
WSACleanup();
因此,我发现前160个字符与标头有关。为了过滤掉标题,我这样做了:
while (buffer[i] >= 32 || buffer[i] == 'n' || buffer[i] == 'r') {
if(i > 160) {
result += buffer[i];
i += 1;
}
}
但是如果标题不一样呢?例如,它使用不同的服务器或其他什么。或者更改了php版本。
我得到的标题作为回应(如果这对某人来说很有趣)
HTTP/1.1 200 OK
Date: Fri, 13 Feb 2015 20:39:56 GMT
Server: Apache
X-Powered-By: PHP/5.3.29
Content-Length: 4
Connection: close
Content-Type: text/html
每次发出请求时,标头都会更改。你不能仅仅假设它是一个固定数量的字节。您必须解析标头。您需要的是:
https://www.ietf.org/rfc/rfc2616.txt
如果您查看第39页,您会发现HTTP标头以空行结束,所以请查找空行,然后内容就在其下方。当然,如果这不仅仅是一个学术练习,你可能会想找到一个为你做这件事的图书馆。HTTP相当复杂。
6响应
在接收并解释请求消息后,服务器进行响应带有HTTP响应消息。
以下是规范的摘录。您想要"消息正文"
Response = Status-Line ; Section 6.1
*(( general-header ; Section 4.5
| response-header ; Section 6.2
| entity-header ) CRLF) ; Section 7.1
CRLF
[ message-body ] ; Section 7.2
相关文章:
- 使用ifstream从DAT文件加载数据
- SqlDataAdapter 未加载数据表 - C++
- C ,MySQL API加载数据本地
- 使用提升库在队列和堆栈数据结构上保存和加载数据时出错
- 使用 fstream 从文件加载数据
- 从文件加载数据
- 将错误处理添加到加载数据的函数(但有时还需要使用默认值)
- C#从文件加载数据并分类为数组
- 保存/加载C++数据时出错
- C++简体版链表,当我加载数据以创建链表并输入更多数据时,似乎存在差距
- 我无法加载数据文件,总是无法打开它
- 从C++模拟中保存和加载数据的有效方法
- 快板 5 加载数据文件
- 通过C++虚幻引擎改进加载数据
- 使用套接字从页面加载数据
- 创建缓冲区以加载数据时出错
- 使用 boost 序列化到磁盘后无法加载数据
- 从C++中的CSV文件读取和加载数据时出现问题
- 如何在运行时通过插件机制动态加载数据类型
- 保存和加载数据C++