From a15d16a9de6d9d5b56cf3ae20c9d0b35e8b98fad Mon Sep 17 00:00:00 2001 From: yhirose Date: Fri, 10 Jan 2020 09:33:14 -0500 Subject: [PATCH] Moved Stream concrete classes into detail namespace --- httplib.h | 139 ++++++++++++++++++++++++++------------------------- test/test.cc | 28 +++++++++-- 2 files changed, 95 insertions(+), 72 deletions(-) diff --git a/httplib.h b/httplib.h index e43d879..742fa7e 100644 --- a/httplib.h +++ b/httplib.h @@ -354,42 +354,6 @@ public: int write_format(const char *fmt, const Args &... args); }; -class SocketStream : public Stream { -public: - SocketStream(socket_t sock, time_t read_timeout_sec, - time_t read_timeout_usec); - ~SocketStream() override; - - int read(char *ptr, size_t size) override; - int write(const char *ptr, size_t size) override; - int write(const char *ptr) override; - int write(const std::string &s) override; - std::string get_remote_addr() const override; - -private: - socket_t sock_; - time_t read_timeout_sec_; - time_t read_timeout_usec_; -}; - -class BufferStream : public Stream { -public: - BufferStream() = default; - ~BufferStream() override = default; - - int read(char *ptr, size_t size) override; - int write(const char *ptr, size_t size) override; - int write(const char *ptr) override; - int write(const std::string &s) override; - std::string get_remote_addr() const override; - - const std::string &get_buffer() const; - -private: - std::string buffer; - int position = 0; -}; - class TaskQueue { public: TaskQueue() = default; @@ -856,26 +820,6 @@ inline void Post(std::vector &requests, const char *path, Post(requests, path, Headers(), body, content_type); } -#ifdef CPPHTTPLIB_OPENSSL_SUPPORT -class SSLSocketStream : public Stream { -public: - SSLSocketStream(socket_t sock, SSL *ssl, time_t read_timeout_sec, - time_t read_timeout_usec); - virtual ~SSLSocketStream(); - - virtual int read(char *ptr, size_t size); - virtual int write(const char *ptr, size_t size); - virtual int write(const char *ptr); - virtual int write(const std::string &s); - virtual std::string get_remote_addr() const; - -private: - socket_t sock_; - SSL *ssl_; - time_t read_timeout_sec_; - time_t read_timeout_usec_; -}; - class SSLServer : public Server { public: SSLServer(const char *cert_path, const char *private_key_path, @@ -1272,6 +1216,62 @@ inline bool wait_until_socket_is_ready(socket_t sock, time_t sec, time_t usec) { #endif } +class SocketStream : public Stream { +public: + SocketStream(socket_t sock, time_t read_timeout_sec, + time_t read_timeout_usec); + ~SocketStream() override; + + int read(char *ptr, size_t size) override; + int write(const char *ptr, size_t size) override; + int write(const char *ptr) override; + int write(const std::string &s) override; + std::string get_remote_addr() const override; + +private: + socket_t sock_; + time_t read_timeout_sec_; + time_t read_timeout_usec_; +}; + +#ifdef CPPHTTPLIB_OPENSSL_SUPPORT +class SSLSocketStream : public Stream { +public: + SSLSocketStream(socket_t sock, SSL *ssl, time_t read_timeout_sec, + time_t read_timeout_usec); + virtual ~SSLSocketStream(); + + virtual int read(char *ptr, size_t size); + virtual int write(const char *ptr, size_t size); + virtual int write(const char *ptr); + virtual int write(const std::string &s); + virtual std::string get_remote_addr() const; + +private: + socket_t sock_; + SSL *ssl_; + time_t read_timeout_sec_; + time_t read_timeout_usec_; +}; + +class BufferStream : public Stream { +public: + BufferStream() = default; + ~BufferStream() override = default; + + int read(char *ptr, size_t size) override; + int write(const char *ptr, size_t size) override; + int write(const char *ptr) override; + int write(const std::string &s) override; + std::string get_remote_addr() const override; + + const std::string &get_buffer() const; + +private: + std::string buffer; + int position = 0; +}; + template inline bool process_socket(bool is_client_request, socket_t sock, size_t keep_alive_max_count, time_t read_timeout_sec, @@ -1284,7 +1284,7 @@ inline bool process_socket(bool is_client_request, socket_t sock, auto count = keep_alive_max_count; while (count > 0 && (is_client_request || - detail::select_read(sock, CPPHTTPLIB_KEEPALIVE_TIMEOUT_SECOND, + select_read(sock, CPPHTTPLIB_KEEPALIVE_TIMEOUT_SECOND, CPPHTTPLIB_KEEPALIVE_TIMEOUT_USECOND) > 0)) { SocketStream strm(sock, read_timeout_sec, read_timeout_usec); auto last_connection = count == 1; @@ -1823,7 +1823,7 @@ bool read_content(Stream &strm, T &x, size_t payload_max_length, int &status, }; #ifdef CPPHTTPLIB_ZLIB_SUPPORT - detail::decompressor decompressor; + decompressor decompressor; if (!decompressor.is_valid()) { status = 500; @@ -2051,7 +2051,7 @@ inline bool parse_range_header(const std::string &s, Ranges &ranges) { auto pos = m.position(1); auto len = m.length(1); bool all_valid_ranges = true; - detail::split( + split( &s[pos], &s[pos + len], ',', [&](const char *b, const char *e) { if (!all_valid_ranges) return; static auto re_another_range = std::regex(R"(\s*(\d*)-(\d*))"); @@ -2317,7 +2317,7 @@ bool process_multipart_ranges_data(const Request &req, Response &res, ctoken("\r\n"); } - auto offsets = detail::get_range_offset_and_length(req, res.body.size(), i); + auto offsets = get_range_offset_and_length(req, res.body.size(), i); auto offset = offsets.first; auto length = offsets.second; @@ -2380,7 +2380,7 @@ inline bool write_multipart_ranges_data(Stream &strm, const Request &req, [&](const std::string &token) { strm.write(token); }, [&](const char *token) { strm.write(token); }, [&](size_t offset, size_t length) { - return detail::write_content(strm, res.content_provider, offset, + return write_content(strm, res.content_provider, offset, length) >= 0; }); } @@ -2425,7 +2425,6 @@ inline std::string message_digest(const std::string &s, Init init, } inline std::string MD5(const std::string &s) { - using namespace detail; return message_digest(s, MD5_Init, MD5_Update, MD5_Final, MD5_DIGEST_LENGTH); } @@ -2717,6 +2716,8 @@ inline int Stream::write_format(const char *fmt, const Args &... args) { } } +namespace detail { + // Socket stream implementation inline SocketStream::SocketStream(socket_t sock, time_t read_timeout_sec, time_t read_timeout_usec) @@ -2776,6 +2777,8 @@ inline std::string BufferStream::get_remote_addr() const { return ""; } inline const std::string &BufferStream::get_buffer() const { return buffer; } +} // namespace detail + // HTTP server implementation inline Server::Server() : keep_alive_max_count_(CPPHTTPLIB_KEEPALIVE_MAX_COUNT), @@ -3678,7 +3681,7 @@ inline bool Client::redirect(const Request &req, Response &res) { inline bool Client::write_request(Stream &strm, const Request &req, bool last_connection) { - BufferStream bstrm; + detail::BufferStream bstrm; // Request line const auto &path = detail::encode_url(req.path); @@ -4333,10 +4336,6 @@ private: #endif }; -static SSLInit sslinit_; - -} // namespace detail - // SSL socket stream implementation inline SSLSocketStream::SSLSocketStream(socket_t sock, SSL *ssl, time_t read_timeout_sec, @@ -4348,7 +4347,7 @@ inline SSLSocketStream::~SSLSocketStream() {} inline int SSLSocketStream::read(char *ptr, size_t size) { if (SSL_pending(ssl_) > 0 || - detail::select_read(sock_, read_timeout_sec_, read_timeout_usec_) > 0) { + select_read(sock_, read_timeout_sec_, read_timeout_usec_) > 0) { return SSL_read(ssl_, ptr, static_cast(size)); } return -1; @@ -4370,6 +4369,10 @@ inline std::string SSLSocketStream::get_remote_addr() const { return detail::get_remote_addr(sock_); } +static SSLInit sslinit_; + +} // namespace detail + // SSL HTTP server implementation inline SSLServer::SSLServer(const char *cert_path, const char *private_key_path, const char *client_ca_cert_file_path, diff --git a/test/test.cc b/test/test.cc index 9a5e4a7..bca6f6a 100644 --- a/test/test.cc +++ b/test/test.cc @@ -199,6 +199,26 @@ TEST(ParseHeaderValueTest, Range) { } } +TEST(BufferStreamTest, read) { + detail::BufferStream strm; + + EXPECT_EQ(5, strm.write("hello")); + + char buf[512]; + EXPECT_EQ(2, strm.read(buf, 2)); + EXPECT_EQ('h', buf[0]); + EXPECT_EQ('e', buf[1]); + + EXPECT_EQ(2, strm.read(buf, 2)); + EXPECT_EQ('l', buf[0]); + EXPECT_EQ('l', buf[1]); + + EXPECT_EQ(1, strm.read(buf, 1)); + EXPECT_EQ('o', buf[0]); + + EXPECT_EQ(0, strm.read(buf, 1)); +} + TEST(ChunkedEncodingTest, FromHTTPWatch) { auto host = "www.httpwatch.com"; @@ -1967,7 +1987,7 @@ TEST(ServerRequestParsingTest, ReadHeadersRegexComplexity) { TEST(ServerStopTest, StopServerWithChunkedTransmission) { Server svr; - svr.Get("/events", [](const Request &req, Response &res) { + svr.Get("/events", [](const Request & /*req*/, Response &res) { res.set_header("Content-Type", "text/event-stream"); res.set_header("Cache-Control", "no-cache"); res.set_chunked_content_provider([](size_t offset, const DataSink &sink) { @@ -1988,9 +2008,9 @@ TEST(ServerStopTest, StopServerWithChunkedTransmission) { {"Connection", "Keep-Alive"}}; auto get_thread = std::thread([&client, &headers]() { - std::shared_ptr res = - client.Get("/events", headers, - [](const char *data, size_t len) -> bool { return true; }); + std::shared_ptr res = client.Get( + "/events", headers, + [](const char * /*data*/, size_t /*len*/) -> bool { return true; }); }); // Give GET time to get a few messages.