@@ -537,6 +537,11 @@ using Progress = std::function<bool(uint64_t current, uint64_t total)>;
537537struct Response ;
538538using ResponseHandler = std::function<bool (const Response &response)>;
539539
540+ class Stream ;
541+ // Note: do not replace 'std::function<bool(Stream &strm)>' with StreamHandler;
542+ // signature is not final
543+ using StreamHandler = std::function<bool (Stream &strm)>;
544+
540545struct MultipartFormData {
541546 std::string name;
542547 std::string content;
@@ -654,6 +659,7 @@ struct Request {
654659
655660 // for client
656661 ResponseHandler response_handler;
662+ StreamHandler stream_handler; // EXPERIMENTAL function signature may change
657663 ContentReceiverWithProgress content_receiver;
658664 Progress progress;
659665#ifdef CPPHTTPLIB_OPENSSL_SUPPORT
@@ -1182,6 +1188,7 @@ enum class Error {
11821188 Compression,
11831189 ConnectionTimeout,
11841190 ProxyConnection,
1191+ StreamHandler,
11851192
11861193 // For internal use only
11871194 SSLPeerCouldBeClosed_,
@@ -2272,6 +2279,7 @@ inline std::string to_string(const Error error) {
22722279 case Error::Compression: return " Compression failed" ;
22732280 case Error::ConnectionTimeout: return " Connection timed out" ;
22742281 case Error::ProxyConnection: return " Proxy connection failed" ;
2282+ case Error::StreamHandler: return " Stream handler failed" ;
22752283 case Error::Unknown: return " Unknown" ;
22762284 default : break ;
22772285 }
@@ -7864,10 +7872,12 @@ inline bool ClientImpl::write_request(Stream &strm, Request &req,
78647872 }
78657873 }
78667874
7867- if (!req.has_header (" Accept" )) { req.set_header (" Accept" , " */*" ); }
7875+ if (!req.stream_handler && !req.has_header (" Accept" )) {
7876+ req.set_header (" Accept" , " */*" );
7877+ }
78687878
78697879 if (!req.content_receiver ) {
7870- if (!req.has_header (" Accept-Encoding" )) {
7880+ if (!req.stream_handler && !req. has_header (" Accept-Encoding" )) {
78717881 std::string accept_encoding;
78727882#ifdef CPPHTTPLIB_BROTLI_SUPPORT
78737883 accept_encoding = " br" ;
@@ -7885,7 +7895,7 @@ inline bool ClientImpl::write_request(Stream &strm, Request &req,
78857895 req.set_header (" User-Agent" , agent);
78867896 }
78877897#endif
7888- };
7898+ }
78897899
78907900 if (req.body .empty ()) {
78917901 if (req.content_provider_ ) {
@@ -8117,10 +8127,23 @@ inline bool ClientImpl::process_request(Stream &strm, Request &req,
81178127 res.status != StatusCode::NotModified_304 &&
81188128 follow_location_;
81198129
8120- if (req.response_handler && !redirect) {
8121- if (!req.response_handler (res)) {
8122- error = Error::Canceled;
8123- return false ;
8130+ if (!redirect) {
8131+ if (req.response_handler ) {
8132+ if (!req.response_handler (res)) {
8133+ error = Error::Canceled;
8134+ return false ;
8135+ }
8136+ }
8137+
8138+ if (req.stream_handler ) {
8139+ // Log early
8140+ if (logger_) { logger_ (req, res); }
8141+
8142+ if (!req.stream_handler (strm)) {
8143+ error = Error::StreamHandler;
8144+ return false ;
8145+ }
8146+ return true ;
81248147 }
81258148 }
81268149
0 commit comments