2 // Copyright (c) 2016-2019 Vinnie Falco (vinnie dot falco at gmail dot com)
4 // Distributed under the Boost Software License, Version 1.0. (See accompanying
5 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
7 // Official repository: https://github.com/boostorg/beast
10 #ifndef BOOST_BEAST_HTTP_WRITE_HPP
11 #define BOOST_BEAST_HTTP_WRITE_HPP
13 #include <boost/beast/core/detail/config.hpp>
14 #include <boost/beast/http/message.hpp>
15 #include <boost/beast/http/serializer.hpp>
16 #include <boost/beast/http/type_traits.hpp>
17 #include <boost/beast/http/detail/chunk_encode.hpp>
18 #include <boost/beast/core/error.hpp>
19 #include <boost/beast/core/stream_traits.hpp>
20 #include <boost/asio/async_result.hpp>
24 #include <type_traits>
31 /** Write part of a message to a stream using a serializer.
33 This function is used to write part of a message to a stream using
34 a caller-provided HTTP/1 serializer. The call will block until one
35 of the following conditions is true:
37 @li One or more bytes have been transferred.
39 @li The function @ref serializer::is_done returns `true`
41 @li An error occurs on the stream.
43 This operation is implemented in terms of one or more calls
44 to the stream's `write_some` function.
46 The amount of data actually transferred is controlled by the behavior
47 of the underlying stream, subject to the buffer size limit of the
48 serializer obtained or set through a call to @ref serializer::limit.
49 Setting a limit and performing bounded work helps applications set
50 reasonable timeouts. It also allows application-level flow control
51 to function correctly. For example when using a TCP/IP based
54 @param stream The stream to which the data is to be written.
55 The type must support the <em>SyncWriteStream</em> concept.
57 @param sr The serializer to use.
59 @return The number of bytes written to the stream.
61 @throws system_error Thrown on failure.
66 class SyncWriteStream,
67 bool isRequest, class Body, class Fields>
70 SyncWriteStream& stream,
71 serializer<isRequest, Body, Fields>& sr);
73 /** Write part of a message to a stream using a serializer.
75 This function is used to write part of a message to a stream using
76 a caller-provided HTTP/1 serializer. The call will block until one
77 of the following conditions is true:
79 @li One or more bytes have been transferred.
81 @li The function @ref serializer::is_done returns `true`
83 @li An error occurs on the stream.
85 This operation is implemented in terms of one or more calls
86 to the stream's `write_some` function.
88 The amount of data actually transferred is controlled by the behavior
89 of the underlying stream, subject to the buffer size limit of the
90 serializer obtained or set through a call to @ref serializer::limit.
91 Setting a limit and performing bounded work helps applications set
92 reasonable timeouts. It also allows application-level flow control
93 to function correctly. For example when using a TCP/IP based
96 @param stream The stream to which the data is to be written.
97 The type must support the <em>SyncWriteStream</em> concept.
99 @param sr The serializer to use.
101 @param ec Set to indicate what error occurred, if any.
103 @return The number of bytes written to the stream.
105 @see async_write_some, serializer
108 class SyncWriteStream,
109 bool isRequest, class Body, class Fields>
112 SyncWriteStream& stream,
113 serializer<isRequest, Body, Fields>& sr,
116 /** Write part of a message to a stream asynchronously using a serializer.
118 This function is used to write part of a message to a stream
119 asynchronously using a caller-provided HTTP/1 serializer. The function
120 call always returns immediately. The asynchronous operation will continue
121 until one of the following conditions is true:
123 @li One or more bytes have been transferred.
125 @li The function @ref serializer::is_done returns `true`
127 @li An error occurs on the stream.
129 This operation is implemented in terms of zero or more calls to the stream's
130 `async_write_some` function, and is known as a <em>composed operation</em>.
131 The program must ensure that the stream performs no other writes
132 until this operation completes.
134 The amount of data actually transferred is controlled by the behavior
135 of the underlying stream, subject to the buffer size limit of the
136 serializer obtained or set through a call to @ref serializer::limit.
137 Setting a limit and performing bounded work helps applications set
138 reasonable timeouts. It also allows application-level flow control
139 to function correctly. For example when using a TCP/IP based
142 @param stream The stream to which the data is to be written.
143 The type must support the <em>AsyncWriteStream</em> concept.
145 @param sr The serializer to use.
146 The object must remain valid at least until the
147 handler is called; ownership is not transferred.
149 @param handler The completion handler to invoke when the operation
150 completes. The implementation takes ownership of the handler by
151 performing a decay-copy. The equivalent function signature of
155 error_code const& error, // result of operation
156 std::size_t bytes_transferred // the number of bytes written to the stream
159 Regardless of whether the asynchronous operation completes
160 immediately or not, the handler will not be invoked from within
161 this function. Invocation of the handler will be performed in a
162 manner equivalent to using `net::post`.
167 class AsyncWriteStream,
168 bool isRequest, class Body, class Fields,
169 BOOST_BEAST_ASYNC_TPARAM2 WriteHandler =
170 net::default_completion_token_t<
171 executor_type<AsyncWriteStream>>>
172 BOOST_BEAST_ASYNC_RESULT2(WriteHandler)
174 AsyncWriteStream& stream,
175 serializer<isRequest, Body, Fields>& sr,
176 WriteHandler&& handler =
177 net::default_completion_token_t<
178 executor_type<AsyncWriteStream>>{});
180 //------------------------------------------------------------------------------
182 /** Write a header to a stream using a serializer.
184 This function is used to write a header to a stream using a
185 caller-provided HTTP/1 serializer. The call will block until one
186 of the following conditions is true:
188 @li The function @ref serializer::is_header_done returns `true`
192 This operation is implemented in terms of one or more calls
193 to the stream's `write_some` function.
195 @param stream The stream to which the data is to be written.
196 The type must support the <em>SyncWriteStream</em> concept.
198 @param sr The serializer to use.
200 @return The number of bytes written to the stream.
202 @throws system_error Thrown on failure.
204 @note The implementation will call @ref serializer::split with
205 the value `true` on the serializer passed in.
210 class SyncWriteStream,
211 bool isRequest, class Body, class Fields>
214 SyncWriteStream& stream,
215 serializer<isRequest, Body, Fields>& sr);
217 /** Write a header to a stream using a serializer.
219 This function is used to write a header to a stream using a
220 caller-provided HTTP/1 serializer. The call will block until one
221 of the following conditions is true:
223 @li The function @ref serializer::is_header_done returns `true`
227 This operation is implemented in terms of one or more calls
228 to the stream's `write_some` function.
230 @param stream The stream to which the data is to be written.
231 The type must support the <em>SyncWriteStream</em> concept.
233 @param sr The serializer to use.
235 @param ec Set to indicate what error occurred, if any.
237 @return The number of bytes written to the stream.
239 @note The implementation will call @ref serializer::split with
240 the value `true` on the serializer passed in.
245 class SyncWriteStream,
246 bool isRequest, class Body, class Fields>
249 SyncWriteStream& stream,
250 serializer<isRequest, Body, Fields>& sr,
253 /** Write a header to a stream asynchronously using a serializer.
255 This function is used to write a header to a stream asynchronously
256 using a caller-provided HTTP/1 serializer. The function call always
257 returns immediately. The asynchronous operation will continue until
258 one of the following conditions is true:
260 @li The function @ref serializer::is_header_done returns `true`
264 This operation is implemented in terms of zero or more calls to the stream's
265 `async_write_some` function, and is known as a <em>composed operation</em>.
266 The program must ensure that the stream performs no other writes
267 until this operation completes.
269 @param stream The stream to which the data is to be written.
270 The type must support the <em>AsyncWriteStream</em> concept.
272 @param sr The serializer to use.
273 The object must remain valid at least until the
274 handler is called; ownership is not transferred.
276 @param handler The completion handler to invoke when the operation
277 completes. The implementation takes ownership of the handler by
278 performing a decay-copy. The equivalent function signature of
282 error_code const& error, // result of operation
283 std::size_t bytes_transferred // the number of bytes written to the stream
286 Regardless of whether the asynchronous operation completes
287 immediately or not, the handler will not be invoked from within
288 this function. Invocation of the handler will be performed in a
289 manner equivalent to using `net::post`.
291 @note The implementation will call @ref serializer::split with
292 the value `true` on the serializer passed in.
297 class AsyncWriteStream,
298 bool isRequest, class Body, class Fields,
299 BOOST_BEAST_ASYNC_TPARAM2 WriteHandler =
300 net::default_completion_token_t<
301 executor_type<AsyncWriteStream>>>
302 BOOST_BEAST_ASYNC_RESULT2(WriteHandler)
304 AsyncWriteStream& stream,
305 serializer<isRequest, Body, Fields>& sr,
306 WriteHandler&& handler =
307 net::default_completion_token_t<
308 executor_type<AsyncWriteStream>>{});
310 //------------------------------------------------------------------------------
312 /** Write a complete message to a stream using a serializer.
314 This function is used to write a complete message to a stream using
315 a caller-provided HTTP/1 serializer. The call will block until one
316 of the following conditions is true:
318 @li The function @ref serializer::is_done returns `true`
322 This operation is implemented in terms of one or more calls
323 to the stream's `write_some` function.
325 @param stream The stream to which the data is to be written.
326 The type must support the <em>SyncWriteStream</em> concept.
328 @param sr The serializer to use.
330 @return The number of bytes written to the stream.
332 @throws system_error Thrown on failure.
337 class SyncWriteStream,
338 bool isRequest, class Body, class Fields>
341 SyncWriteStream& stream,
342 serializer<isRequest, Body, Fields>& sr);
344 /** Write a complete message to a stream using a serializer.
346 This function is used to write a complete message to a stream using
347 a caller-provided HTTP/1 serializer. The call will block until one
348 of the following conditions is true:
350 @li The function @ref serializer::is_done returns `true`
354 This operation is implemented in terms of one or more calls
355 to the stream's `write_some` function.
357 @param stream The stream to which the data is to be written.
358 The type must support the <em>SyncWriteStream</em> concept.
360 @param sr The serializer to use.
362 @param ec Set to the error, if any occurred.
364 @return The number of bytes written to the stream.
369 class SyncWriteStream,
370 bool isRequest, class Body, class Fields>
373 SyncWriteStream& stream,
374 serializer<isRequest, Body, Fields>& sr,
377 /** Write a complete message to a stream asynchronously using a serializer.
379 This function is used to write a complete message to a stream
380 asynchronously using a caller-provided HTTP/1 serializer. The
381 function call always returns immediately. The asynchronous
382 operation will continue until one of the following conditions is true:
384 @li The function @ref serializer::is_done returns `true`
388 This operation is implemented in terms of zero or more calls to the stream's
389 `async_write_some` function, and is known as a <em>composed operation</em>.
390 The program must ensure that the stream performs no other writes
391 until this operation completes.
393 @param stream The stream to which the data is to be written.
394 The type must support the <em>AsyncWriteStream</em> concept.
396 @param sr The serializer to use.
397 The object must remain valid at least until the
398 handler is called; ownership is not transferred.
400 @param handler The completion handler to invoke when the operation
401 completes. The implementation takes ownership of the handler by
402 performing a decay-copy. The equivalent function signature of
406 error_code const& error, // result of operation
407 std::size_t bytes_transferred // the number of bytes written to the stream
410 Regardless of whether the asynchronous operation completes
411 immediately or not, the handler will not be invoked from within
412 this function. Invocation of the handler will be performed in a
413 manner equivalent to using `net::post`.
418 class AsyncWriteStream,
419 bool isRequest, class Body, class Fields,
420 BOOST_BEAST_ASYNC_TPARAM2 WriteHandler =
421 net::default_completion_token_t<
422 executor_type<AsyncWriteStream>>>
423 BOOST_BEAST_ASYNC_RESULT2(WriteHandler)
425 AsyncWriteStream& stream,
426 serializer<isRequest, Body, Fields>& sr,
427 WriteHandler&& handler =
428 net::default_completion_token_t<
429 executor_type<AsyncWriteStream>>{});
431 //------------------------------------------------------------------------------
433 /** Write a complete message to a stream.
435 This function is used to write a complete message to a stream using
436 HTTP/1. The call will block until one of the following conditions is true:
438 @li The entire message is written.
442 This operation is implemented in terms of one or more calls to the stream's
443 `write_some` function. The algorithm will use a temporary @ref serializer
444 with an empty chunk decorator to produce buffers.
446 @note This function only participates in overload resolution
447 if @ref is_mutable_body_writer for <em>Body</em> returns `true`.
449 @param stream The stream to which the data is to be written.
450 The type must support the <em>SyncWriteStream</em> concept.
452 @param msg The message to write.
454 @return The number of bytes written to the stream.
456 @throws system_error Thrown on failure.
461 class SyncWriteStream,
462 bool isRequest, class Body, class Fields>
463 #if BOOST_BEAST_DOXYGEN
466 typename std::enable_if<
467 is_mutable_body_writer<Body>::value,
471 SyncWriteStream& stream,
472 message<isRequest, Body, Fields>& msg);
474 /** Write a complete message to a stream.
476 This function is used to write a complete message to a stream using
477 HTTP/1. The call will block until one of the following conditions is true:
479 @li The entire message is written.
483 This operation is implemented in terms of one or more calls to the stream's
484 `write_some` function. The algorithm will use a temporary @ref serializer
485 with an empty chunk decorator to produce buffers.
487 @note This function only participates in overload resolution
488 if @ref is_mutable_body_writer for <em>Body</em> returns `false`.
490 @param stream The stream to which the data is to be written.
491 The type must support the <em>SyncWriteStream</em> concept.
493 @param msg The message to write.
495 @return The number of bytes written to the stream.
497 @throws system_error Thrown on failure.
502 class SyncWriteStream,
503 bool isRequest, class Body, class Fields>
504 #if BOOST_BEAST_DOXYGEN
507 typename std::enable_if<
508 ! is_mutable_body_writer<Body>::value,
512 SyncWriteStream& stream,
513 message<isRequest, Body, Fields> const& msg);
515 /** Write a complete message to a stream.
517 This function is used to write a complete message to a stream using
518 HTTP/1. The call will block until one of the following conditions is true:
520 @li The entire message is written.
524 This operation is implemented in terms of one or more calls to the stream's
525 `write_some` function. The algorithm will use a temporary @ref serializer
526 with an empty chunk decorator to produce buffers.
528 @note This function only participates in overload resolution
529 if @ref is_mutable_body_writer for <em>Body</em> returns `true`.
531 @param stream The stream to which the data is to be written.
532 The type must support the <em>SyncWriteStream</em> concept.
534 @param msg The message to write.
536 @param ec Set to the error, if any occurred.
538 @return The number of bytes written to the stream.
543 class SyncWriteStream,
544 bool isRequest, class Body, class Fields>
545 #if BOOST_BEAST_DOXYGEN
548 typename std::enable_if<
549 is_mutable_body_writer<Body>::value,
553 SyncWriteStream& stream,
554 message<isRequest, Body, Fields>& msg,
557 /** Write a complete message to a stream.
559 This function is used to write a complete message to a stream using
560 HTTP/1. The call will block until one of the following conditions is true:
562 @li The entire message is written.
566 This operation is implemented in terms of one or more calls to the stream's
567 `write_some` function. The algorithm will use a temporary @ref serializer
568 with an empty chunk decorator to produce buffers.
570 @note This function only participates in overload resolution
571 if @ref is_mutable_body_writer for <em>Body</em> returns `false`.
573 @param stream The stream to which the data is to be written.
574 The type must support the <em>SyncWriteStream</em> concept.
576 @param msg The message to write.
578 @param ec Set to the error, if any occurred.
580 @return The number of bytes written to the stream.
585 class SyncWriteStream,
586 bool isRequest, class Body, class Fields>
587 #if BOOST_BEAST_DOXYGEN
590 typename std::enable_if<
591 ! is_mutable_body_writer<Body>::value,
595 SyncWriteStream& stream,
596 message<isRequest, Body, Fields> const& msg,
599 /** Write a complete message to a stream asynchronously.
601 This function is used to write a complete message to a stream asynchronously
602 using HTTP/1. The function call always returns immediately. The asynchronous
603 operation will continue until one of the following conditions is true:
605 @li The entire message is written.
609 This operation is implemented in terms of zero or more calls to the stream's
610 `async_write_some` function, and is known as a <em>composed operation</em>.
611 The program must ensure that the stream performs no other writes
612 until this operation completes. The algorithm will use a temporary
613 @ref serializer with an empty chunk decorator to produce buffers.
615 @note This function only participates in overload resolution
616 if @ref is_mutable_body_writer for <em>Body</em> returns `true`.
618 @param stream The stream to which the data is to be written.
619 The type must support the <em>AsyncWriteStream</em> concept.
621 @param msg The message to write.
622 The object must remain valid at least until the
623 handler is called; ownership is not transferred.
625 @param handler The completion handler to invoke when the operation
626 completes. The implementation takes ownership of the handler by
627 performing a decay-copy. The equivalent function signature of
631 error_code const& error, // result of operation
632 std::size_t bytes_transferred // the number of bytes written to the stream
635 Regardless of whether the asynchronous operation completes
636 immediately or not, the handler will not be invoked from within
637 this function. Invocation of the handler will be performed in a
638 manner equivalent to using `net::post`.
643 class AsyncWriteStream,
644 bool isRequest, class Body, class Fields,
645 BOOST_BEAST_ASYNC_TPARAM2 WriteHandler =
646 net::default_completion_token_t<
647 executor_type<AsyncWriteStream>>>
648 BOOST_BEAST_ASYNC_RESULT2(WriteHandler)
650 AsyncWriteStream& stream,
651 message<isRequest, Body, Fields>& msg,
652 WriteHandler&& handler =
653 net::default_completion_token_t<
654 executor_type<AsyncWriteStream>>{}
655 #ifndef BOOST_BEAST_DOXYGEN
656 , typename std::enable_if<
657 is_mutable_body_writer<Body>::value>::type* = 0
661 /** Write a complete message to a stream asynchronously.
663 This function is used to write a complete message to a stream asynchronously
664 using HTTP/1. The function call always returns immediately. The asynchronous
665 operation will continue until one of the following conditions is true:
667 @li The entire message is written.
671 This operation is implemented in terms of zero or more calls to the stream's
672 `async_write_some` function, and is known as a <em>composed operation</em>.
673 The program must ensure that the stream performs no other writes
674 until this operation completes. The algorithm will use a temporary
675 @ref serializer with an empty chunk decorator to produce buffers.
677 @note This function only participates in overload resolution
678 if @ref is_mutable_body_writer for <em>Body</em> returns `false`.
680 @param stream The stream to which the data is to be written.
681 The type must support the <em>AsyncWriteStream</em> concept.
683 @param msg The message to write.
684 The object must remain valid at least until the
685 handler is called; ownership is not transferred.
687 @param handler The completion handler to invoke when the operation
688 completes. The implementation takes ownership of the handler by
689 performing a decay-copy. The equivalent function signature of
693 error_code const& error, // result of operation
694 std::size_t bytes_transferred // the number of bytes written to the stream
697 Regardless of whether the asynchronous operation completes
698 immediately or not, the handler will not be invoked from within
699 this function. Invocation of the handler will be performed in a
700 manner equivalent to using `net::post`.
705 class AsyncWriteStream,
706 bool isRequest, class Body, class Fields,
707 BOOST_BEAST_ASYNC_TPARAM2 WriteHandler =
708 net::default_completion_token_t<
709 executor_type<AsyncWriteStream>>>
710 BOOST_BEAST_ASYNC_RESULT2(WriteHandler)
712 AsyncWriteStream& stream,
713 message<isRequest, Body, Fields> const& msg,
714 WriteHandler&& handler =
715 net::default_completion_token_t<
716 executor_type<AsyncWriteStream>>{}
717 #ifndef BOOST_BEAST_DOXYGEN
718 , typename std::enable_if<
719 ! is_mutable_body_writer<Body>::value>::type* = 0
724 //------------------------------------------------------------------------------
726 /** Serialize an HTTP/1 header to a `std::ostream`.
728 The function converts the header to its HTTP/1 serialized
729 representation and stores the result in the output stream.
731 @param os The output stream to write to.
733 @param msg The message fields to write.
735 template<bool isRequest, class Fields>
737 operator<<(std::ostream& os,
738 header<isRequest, Fields> const& msg);
740 /** Serialize an HTTP/1 message to a `std::ostream`.
742 The function converts the message to its HTTP/1 serialized
743 representation and stores the result in the output stream.
745 The implementation will automatically perform chunk encoding if
746 the contents of the message indicate that chunk encoding is required.
748 @param os The output stream to write to.
750 @param msg The message to write.
752 template<bool isRequest, class Body, class Fields>
754 operator<<(std::ostream& os,
755 message<isRequest, Body, Fields> const& msg);
761 #include <boost/beast/http/impl/write.hpp>