有什么方法可以简单地用c++发出HTTP请求吗?具体来说,我想下载一个页面(一个API)的内容,并检查内容,看看它是否包含1或0。是否也可以将内容下载到字符串中?
当前回答
C和c++没有用于HTTP甚至套接字连接的标准库。多年来,一些便携式图书馆已经被开发出来。正如其他人所说,使用最广泛的是libcurl。
下面是libcurl的替代品列表(来自libcurl的网站)。
另外,对于Linux,这是一个简单的HTTP客户机。您可以实现自己的简单HTTP GET客户端,但如果涉及到身份验证或重定向,或者需要在代理后工作,则这将不起作用。对于这些情况,您需要像libcurl这样成熟的库。
对于使用libcurl的源代码,这是最接近您想要的(libcurl有许多示例)。看看主要功能。成功连接后,html内容将被复制到缓冲区。只需用自己的函数替换parseHtml即可。
其他回答
如果你想要c++的解决方案,你可以使用Qt,它有一个QHttp类。
你可以查看文档:
http->setHost("qt.nokia.com");
http->get(QUrl::toPercentEncoding("/index.html"));
Qt还有很多可以在普通c++应用程序中使用的功能。
2020年4月的最新答案:
最近,我使用cppp -httplib(作为客户机和服务器)取得了很大的成功。它是成熟的,它的近似,单线程RPS约为6k。
更先进的是,有一个非常有前途的框架,cpv-framework,它可以在两个核上获得大约180k RPS(并且可以很好地扩展核的数量,因为它基于sestar框架,它为地球上最快的db scylladb提供动力)。
但是cpv-framework还比较不成熟;所以,对于大多数用途,我强烈推荐cppp -httplib。
这个建议取代了我之前的答案(8年前)。
下面是一些(相对)简单的c++ 11代码,使用libCURL将URL的内容下载到std::vector<char>:
http_download.hh
# pragma once
#include <string>
#include <vector>
std::vector<char> download(std::string url, long* responseCode = nullptr);
http_download.cc
#include "http_download.hh"
#include <curl/curl.h>
#include <sstream>
#include <stdexcept>
using namespace std;
size_t callback(void* contents, size_t size, size_t nmemb, void* user)
{
auto chunk = reinterpret_cast<char*>(contents);
auto buffer = reinterpret_cast<vector<char>*>(user);
size_t priorSize = buffer->size();
size_t sizeIncrease = size * nmemb;
buffer->resize(priorSize + sizeIncrease);
std::copy(chunk, chunk + sizeIncrease, buffer->data() + priorSize);
return sizeIncrease;
}
vector<char> download(string url, long* responseCode)
{
vector<char> data;
curl_global_init(CURL_GLOBAL_ALL);
CURL* handle = curl_easy_init();
curl_easy_setopt(handle, CURLOPT_URL, url.c_str());
curl_easy_setopt(handle, CURLOPT_WRITEFUNCTION, callback);
curl_easy_setopt(handle, CURLOPT_WRITEDATA, &data);
curl_easy_setopt(handle, CURLOPT_USERAGENT, "libcurl-agent/1.0");
CURLcode result = curl_easy_perform(handle);
if (responseCode != nullptr)
curl_easy_getinfo(handle, CURLINFO_RESPONSE_CODE, responseCode);
curl_easy_cleanup(handle);
curl_global_cleanup();
if (result != CURLE_OK)
{
stringstream err;
err << "Error downloading from URL \"" << url << "\": " << curl_easy_strerror(result);
throw runtime_error(err.str());
}
return data;
}
2020年更新:我有一个新的答案来取代这个已经存在了8年的答案:https://stackoverflow.com/a/61177330/278976
在Linux上,我尝试了cppp -netlib、libcurl、curlpp、urdl、boost::asio,并考虑过Qt(但基于许可证拒绝了它)。所有这些都不是不完整的,有草率的界面,有糟糕的文档,没有维护或不支持https。
然后,在https://stackoverflow.com/a/1012577/278976的建议下,我尝试了POCO。哇,我真希望几年前就能看到。下面是一个使用POCO进行HTTP GET请求的示例:
https://stackoverflow.com/a/26026828/2817595
POCO是免费的、开源的(boost许可证)。不,我和这家公司没有任何关系;我真的很喜欢他们的界面。干得好,伙计们(和姑娘们)。
https://pocoproject.org/download.html
希望这能帮助到某人…我花了三天时间把所有这些库都试了一遍。
我也有同样的问题。Libcurl真的很完整。如果您需要c++库,可能会对c++包装器curlpp感兴趣。neon是另一个有趣的C库,它也支持WebDAV。
如果你使用c++, curlpp看起来很自然。源代码发行版中提供了许多示例。 要获取URL的内容,你可以这样做(从示例中提取):
// Edit : rewritten for cURLpp 0.7.3
// Note : namespace changed, was cURLpp in 0.7.2 ...
#include <curlpp/cURLpp.hpp>
#include <curlpp/Options.hpp>
// RAII cleanup
curlpp::Cleanup myCleanup;
// Send request and get a result.
// Here I use a shortcut to get it in a string stream ...
std::ostringstream os;
os << curlpp::options::Url(std::string("http://example.com"));
string asAskedInQuestion = os.str();
参见curlpp源代码分发中的示例目录,有很多更复杂的情况,以及使用curlpp的简单完整的最小情况。
我的2美分…