Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 34 additions & 20 deletions httplib.h
Original file line number Diff line number Diff line change
Expand Up @@ -724,6 +724,8 @@ class Client {

void set_compress(bool on);

void set_decompress(bool on);

void set_interface(const char *intf);

void set_proxy(const char *host, int port);
Expand Down Expand Up @@ -767,6 +769,8 @@ class Client {

bool compress_ = false;

bool decompress_ = true;

std::string interface_;

std::string proxy_host_;
Expand Down Expand Up @@ -796,6 +800,7 @@ class Client {
#endif
follow_location_ = rhs.follow_location_;
compress_ = rhs.compress_;
decompress_ = rhs.decompress_;
interface_ = rhs.interface_;
proxy_host_ = rhs.proxy_host_;
proxy_port_ = rhs.proxy_port_;
Expand Down Expand Up @@ -2004,34 +2009,36 @@ inline bool is_chunked_transfer_encoding(const Headers &headers) {

template <typename T>
bool read_content(Stream &strm, T &x, size_t payload_max_length, int &status,
Progress progress, ContentReceiver receiver) {
Progress progress, ContentReceiver receiver, bool decompress) {

ContentReceiver out = [&](const char *buf, size_t n) {
return receiver(buf, n);
};

if (decompress) {
#ifdef CPPHTTPLIB_ZLIB_SUPPORT
decompressor decompressor;
decompressor decompressor;

std::string content_encoding = x.get_header_value("Content-Encoding");
if (content_encoding.find("gzip") != std::string::npos ||
content_encoding.find("deflate") != std::string::npos) {
if (!decompressor.is_valid()) {
status = 500;
return false;
}
std::string content_encoding = x.get_header_value("Content-Encoding");
if (content_encoding.find("gzip") != std::string::npos ||
content_encoding.find("deflate") != std::string::npos) {
if (!decompressor.is_valid()) {
status = 500;
return false;
}

out = [&](const char *buf, size_t n) {
return decompressor.decompress(
buf, n, [&](const char *buf, size_t n) { return receiver(buf, n); });
};
}
out = [&](const char *buf, size_t n) {
return decompressor.decompress(
buf, n, [&](const char *buf, size_t n) { return receiver(buf, n); });
};
}
#else
if (x.get_header_value("Content-Encoding") == "gzip") {
status = 415;
return false;
}
if (x.get_header_value("Content-Encoding") == "gzip") {
status = 415;
return false;
}
#endif
}

auto ret = true;
auto exceed_payload_max_length = false;
Expand Down Expand Up @@ -3462,7 +3469,7 @@ inline bool Server::read_content_core(Stream &strm, Request &req, Response &res,
}

if (!detail::read_content(strm, req, payload_max_length_, res.status,
Progress(), out)) {
Progress(), out, true)) {
return false;
}

Expand Down Expand Up @@ -4234,7 +4241,7 @@ inline bool Client::process_request(Stream &strm, const Request &req,

int dummy_status;
if (!detail::read_content(strm, res, (std::numeric_limits<size_t>::max)(),
dummy_status, req.progress, out)) {
dummy_status, req.progress, out, decompress_)) {
return false;
}
}
Expand Down Expand Up @@ -4586,6 +4593,8 @@ inline void Client::set_follow_location(bool on) { follow_location_ = on; }

inline void Client::set_compress(bool on) { compress_ = on; }

inline void Client::set_decompress(bool on) { decompress_ = on; }

inline void Client::set_interface(const char *intf) { interface_ = intf; }

inline void Client::set_proxy(const char *host, int port) {
Expand Down Expand Up @@ -5391,6 +5400,11 @@ class Client2 {
return *this;
}

Client2 &set_decompress(bool on) {
cli_->set_decompress(on);
return *this;
}

Client2 &set_interface(const char *intf) {
cli_->set_interface(intf);
return *this;
Expand Down
15 changes: 15 additions & 0 deletions test/test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2266,6 +2266,21 @@ TEST_F(ServerTest, MultipartFormDataGzip) {
ASSERT_TRUE(res != nullptr);
EXPECT_EQ(200, res->status);
}

TEST_F(ServerTest, GzipWithoutDecompressing) {
Headers headers;
headers.emplace("Accept-Encoding", "gzip, deflate");

cli_.set_decompress(false);

auto res = cli_.Get("/gzip", headers);

ASSERT_TRUE(res != nullptr);
EXPECT_EQ("gzip", res->get_header_value("Content-Encoding"));
EXPECT_EQ("application/json", res->get_header_value("Content-Type"));
EXPECT_EQ("202", res->get_header_value("Content-Length"));
EXPECT_EQ(200, res->status);
}
#endif

// Sends a raw request to a server listening at HOST:PORT.
Expand Down