Compare commits

..

11 Commits

Author SHA1 Message Date
yhirose 615867322d Fixed build errors and apply clangformat 2020-11-29 12:29:18 -05:00
David Wu 02d3cd5909 Fix multiple threading bugs including #699 and #697 2020-11-29 12:29:15 -05:00
yhirose 47e5af15ea Updated README 2020-11-22 09:22:40 -05:00
yhirose a5c239c174 Fix #765 2020-11-21 16:35:31 -05:00
yhirose c2afc5ca44 Added chunked content provider support on client 2020-11-21 08:46:50 -05:00
yhirose cee062d4c9 Fixed unit tests due to the change in #763 2020-11-19 21:04:46 -05:00
Unkorunk b21dc8cbe0 Fix incorrect content_encoding for Brotli (#763) 2020-11-19 12:39:20 -05:00
372046933 e1133a2dcb std::tolower is undefined if the argument's value is neither representable as unsigned char nor equal to EOF (#761)
Co-authored-by: taoxu <taoxu@bilibili.com>
2020-11-19 09:21:40 -05:00
yhirose e273fec93c Fixed Visual Studio setup 2020-11-19 09:17:59 -05:00
yhirose 95d0b073bd Fix #754 2020-11-15 08:13:08 -05:00
vawen 9c7d841b37 Fix: #746 Compile error under VS2015 (#747)
Co-authored-by: jigarcia@vaxtor.es <jigarcia@vaxtor.es>
2020-11-10 08:41:53 -05:00
5 changed files with 573 additions and 191 deletions
+1 -1
View File
@@ -32,7 +32,7 @@ jobs:
run: cd test && make -f Makefile.fuzz_test
- name: setup msbuild on windows
if: matrix.os == 'windows-latest'
uses: warrenbuckley/Setup-MSBuild@v1
uses: microsoft/setup-msbuild@v1.0.2
- name: make-windows
if: matrix.os == 'windows-latest'
run: |
+22 -1
View File
@@ -502,7 +502,7 @@ auto res = cli.Get(
```cpp
std::string body = ...;
auto res = cli_.Post(
auto res = cli.Post(
"/stream", body.size(),
[](size_t offset, size_t length, DataSink &sink) {
sink.write(body.data() + offset, length);
@@ -511,6 +511,21 @@ auto res = cli_.Post(
"text/plain");
```
### Chunked transfer encoding
```cpp
auto res = cli.Post(
"/stream",
[](size_t offset, DataSink &sink) {
sink.os << "chunked data 1";
sink.os << "chunked data 2";
sink.os << "chunked data 3";
sink.done();
return true; // return 'false' if you want to cancel the request.
},
"text/plain");
```
### With Progress Callback
```cpp
@@ -630,6 +645,12 @@ cli.set_ca_cert_path("./ca-bundle.crt");
cli.enable_server_certificate_verification(true);
```
Note: When using SSL, it seems impossible to avoid SIGPIPE in all cases, since on some operating systems, SIGPIPE
can only be suppressed on a per-message basis, but there is no way to make the OpenSSL library do so for its
internal communications. If your program needs to avoid being terminated on SIGPIPE, the only fully general way might
be to set up a signal handler for SIGPIPE to handle or ignore it yourself.
Compression
-----------
+483 -183
View File
File diff suppressed because it is too large Load Diff
+2
View File
@@ -35,6 +35,8 @@ class FuzzedStream : public httplib::Stream {
port = 8080;
}
socket_t socket() const override { return 0; }
private:
const uint8_t* data_;
size_t size_;
+65 -6
View File
@@ -5,6 +5,7 @@
#include <chrono>
#include <future>
#include <thread>
#include <atomic>
#define SERVER_CERT_FILE "./cert.pem"
#define SERVER_CERT2_FILE "./cert2.pem"
@@ -778,6 +779,7 @@ TEST(YahooRedirectTest, Redirect) {
res = cli.Get("/");
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("https://yahoo.com/", res->location);
}
#if 0
@@ -1434,6 +1436,7 @@ TEST_F(ServerTest, GetMethod302Redirect) {
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("Hello World!", res->body);
EXPECT_EQ("/hi", res->location);
}
TEST_F(ServerTest, GetMethod404) {
@@ -1662,6 +1665,7 @@ TEST_F(ServerTest, PostMethod303Redirect) {
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("redirected.", res->body);
EXPECT_EQ("/2", res->location);
}
TEST_F(ServerTest, UserDefinedMIMETypeMapping) {
@@ -2217,6 +2221,31 @@ TEST_F(ServerTest, PostWithContentProviderAbort) {
EXPECT_EQ(Error::Canceled, res.error());
}
TEST_F(ServerTest, PutWithContentProviderWithoutLength) {
auto res = cli_.Put(
"/put",
[](size_t /*offset*/, DataSink &sink) {
EXPECT_TRUE(sink.is_writable());
sink.os << "PUT";
sink.done();
return true;
},
"text/plain");
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("PUT", res->body);
}
TEST_F(ServerTest, PostWithContentProviderWithoutLengthAbort) {
auto res = cli_.Post(
"/post", [](size_t /*offset*/, DataSink & /*sink*/) { return false; },
"text/plain");
ASSERT_TRUE(!res);
EXPECT_EQ(Error::Canceled, res.error());
}
#ifdef CPPHTTPLIB_ZLIB_SUPPORT
TEST_F(ServerTest, PutWithContentProviderWithGzip) {
cli_.set_compress(true);
@@ -2247,6 +2276,33 @@ TEST_F(ServerTest, PostWithContentProviderWithGzipAbort) {
EXPECT_EQ(Error::Canceled, res.error());
}
TEST_F(ServerTest, PutWithContentProviderWithoutLengthWithGzip) {
cli_.set_compress(true);
auto res = cli_.Put(
"/put",
[](size_t /*offset*/, DataSink &sink) {
EXPECT_TRUE(sink.is_writable());
sink.os << "PUT";
sink.done();
return true;
},
"text/plain");
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("PUT", res->body);
}
TEST_F(ServerTest, PostWithContentProviderWithoutLengthWithGzipAbort) {
cli_.set_compress(true);
auto res = cli_.Post(
"/post", [](size_t /*offset*/, DataSink & /*sink*/) { return false; },
"text/plain");
ASSERT_TRUE(!res);
EXPECT_EQ(Error::Canceled, res.error());
}
TEST_F(ServerTest, PutLargeFileWithGzip) {
cli_.set_compress(true);
auto res = cli_.Put("/put-large", LARGE_DATA, "text/plain");
@@ -2334,7 +2390,7 @@ TEST(GzipDecompressor, ChunkedDecompression) {
#ifdef CPPHTTPLIB_BROTLI_SUPPORT
TEST_F(ServerTest, GetStreamedChunkedWithBrotli) {
Headers headers;
headers.emplace("Accept-Encoding", "brotli");
headers.emplace("Accept-Encoding", "br");
auto res = cli_.Get("/streamed-chunked", headers);
ASSERT_TRUE(res);
@@ -2344,7 +2400,7 @@ TEST_F(ServerTest, GetStreamedChunkedWithBrotli) {
TEST_F(ServerTest, GetStreamedChunkedWithBrotli2) {
Headers headers;
headers.emplace("Accept-Encoding", "brotli");
headers.emplace("Accept-Encoding", "br");
auto res = cli_.Get("/streamed-chunked2", headers);
ASSERT_TRUE(res);
@@ -2693,7 +2749,7 @@ TEST_F(ServerTest, Brotli) {
auto res = cli_.Get("/compress", headers);
ASSERT_TRUE(res);
EXPECT_EQ("brotli", res->get_header_value("Content-Encoding"));
EXPECT_EQ("br", res->get_header_value("Content-Encoding"));
EXPECT_EQ("text/plain", res->get_header_value("Content-Type"));
EXPECT_EQ("19", res->get_header_value("Content-Length"));
EXPECT_EQ("123456789012345678901234567890123456789012345678901234567890123456"
@@ -2706,7 +2762,7 @@ TEST_F(ServerTest, Brotli) {
// Sends a raw request to a server listening at HOST:PORT.
static bool send_request(time_t read_timeout_sec, const std::string &req,
std::string *resp = nullptr) {
Error error = Error::Success;
std::atomic<Error> error(Error::Success);
auto client_sock =
detail::create_client_socket(HOST, PORT, false, nullptr,
@@ -3586,6 +3642,7 @@ TEST(YahooRedirectTest2, SimpleInterface) {
res = cli.Get("/");
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("https://yahoo.com/", res->location);
}
TEST(YahooRedirectTest3, SimpleInterface) {
@@ -3599,6 +3656,7 @@ TEST(YahooRedirectTest3, SimpleInterface) {
res = cli.Get("/");
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);
EXPECT_EQ("https://www.yahoo.com/", res->location);
}
TEST(YahooRedirectTest3, NewResultInterface) {
@@ -3622,13 +3680,14 @@ TEST(YahooRedirectTest3, NewResultInterface) {
EXPECT_EQ(200, res.value().status);
EXPECT_EQ(200, (*res).status);
EXPECT_EQ(200, res->status);
EXPECT_EQ("https://www.yahoo.com/", res->location);
}
#ifdef CPPHTTPLIB_BROTLI_SUPPORT
TEST(DecodeWithChunkedEncoding, BrotliEncoding) {
Client cli("https://cdnjs.cloudflare.com");
auto res = cli.Get("/ajax/libs/jquery/3.5.1/jquery.js",
{{"Accept-Encoding", "brotli"}});
auto res =
cli.Get("/ajax/libs/jquery/3.5.1/jquery.js", {{"Accept-Encoding", "br"}});
ASSERT_TRUE(res);
EXPECT_EQ(200, res->status);