forked from boostorg/beast
websocket documentation
This commit is contained in:
@@ -15,6 +15,7 @@ WebSocket:
|
|||||||
* Call do_fail from read_some
|
* Call do_fail from read_some
|
||||||
* eof on accept returns error::closed
|
* eof on accept returns error::closed
|
||||||
* Fix stream::read_size_hint calculation
|
* Fix stream::read_size_hint calculation
|
||||||
|
* Documentation
|
||||||
|
|
||||||
API Changes:
|
API Changes:
|
||||||
|
|
||||||
|
@@ -35,6 +35,7 @@ Boost.Asio with a consistent asynchronous model using a modern C++ approach.
|
|||||||
[include 06_websocket/4_server.qbk]
|
[include 06_websocket/4_server.qbk]
|
||||||
[include 06_websocket/5_messages.qbk]
|
[include 06_websocket/5_messages.qbk]
|
||||||
[include 06_websocket/6_control.qbk]
|
[include 06_websocket/6_control.qbk]
|
||||||
[include 06_websocket/7_notes.qbk]
|
[include 06_websocket/7_teardown.qbk]
|
||||||
|
[include 06_websocket/8_notes.qbk]
|
||||||
|
|
||||||
[endsect]
|
[endsect]
|
||||||
|
@@ -35,7 +35,7 @@ and `ssl::context` arguments are forwarded to the wrapped stream's constructor:
|
|||||||
|
|
||||||
[important
|
[important
|
||||||
Code which declares websocket stream objects using Asio SSL types
|
Code which declares websocket stream objects using Asio SSL types
|
||||||
must include the file [include_file beast/websocket/ssl.hpp].
|
must include the file [include_file boost/beast/websocket/ssl.hpp].
|
||||||
]
|
]
|
||||||
|
|
||||||
[heading Non-owning References]
|
[heading Non-owning References]
|
||||||
|
@@ -13,9 +13,11 @@ A
|
|||||||
[link beast.ref.boost__beast__websocket__stream `stream`]
|
[link beast.ref.boost__beast__websocket__stream `stream`]
|
||||||
automatically handles receiving and processing the HTTP response to the
|
automatically handles receiving and processing the HTTP response to the
|
||||||
handshake request. The call to handshake is successful if a HTTP response
|
handshake request. The call to handshake is successful if a HTTP response
|
||||||
is received with the 101 "Switching Protocols" status code. On failure,
|
is received with the
|
||||||
an error is returned or an exception is thrown. Depending on the keep alive
|
[@https://tools.ietf.org/html/rfc6455#section-4.2.2 ['101 Switching Protocols]]
|
||||||
setting, the connection may remain open for a subsequent handshake attempt.
|
status code. On failure, an error is returned or an exception is thrown.
|
||||||
|
Depending on the keep alive setting, the connection may remain open for
|
||||||
|
a subsequent handshake attempt.
|
||||||
|
|
||||||
Performing a handshake for an incoming websocket upgrade request operates
|
Performing a handshake for an incoming websocket upgrade request operates
|
||||||
similarly. If the handshake fails, an error is returned or exception thrown:
|
similarly. If the handshake fails, an error is returned or exception thrown:
|
||||||
@@ -36,8 +38,10 @@ typically look like this:
|
|||||||
Server: Beast/40
|
Server: Beast/40
|
||||||
```
|
```
|
||||||
][
|
][
|
||||||
The Sec-WebSocket-Accept field value is generated from the
|
The
|
||||||
request in a fashion specified by the WebSocket protocol.
|
[@https://tools.ietf.org/html/rfc6455#section-11.3.3 ['Sec-WebSocket-Accept]]
|
||||||
|
field value is generated from the request in a fashion specified by
|
||||||
|
the WebSocket protocol.
|
||||||
]]]
|
]]]
|
||||||
|
|
||||||
[heading Decorators]
|
[heading Decorators]
|
||||||
@@ -115,4 +119,13 @@ area, and later uses those octets to attempt an HTTP WebSocket Upgrade:
|
|||||||
|
|
||||||
[ws_snippet_14]
|
[ws_snippet_14]
|
||||||
|
|
||||||
|
The implementation uses a fixed-size storage area to hold buffers passed
|
||||||
|
using these functions. If an application is reaching the limit of the
|
||||||
|
internal buffer size, then the websocket stream may be instantiated with
|
||||||
|
the next layer type of
|
||||||
|
[link beast.ref.boost__beast__buffered_read_stream `buffered_read_stream`]
|
||||||
|
to wrap the underlying stream. The buffered handshake data may be first
|
||||||
|
placed into the buffered read stream, which uses a dynamically sized
|
||||||
|
buffer.
|
||||||
|
|
||||||
[endsect]
|
[endsect]
|
||||||
|
@@ -9,6 +9,51 @@
|
|||||||
|
|
||||||
[section Send and Receive Messages]
|
[section Send and Receive Messages]
|
||||||
|
|
||||||
|
Interfaces for transacting messages are structured into a couple of
|
||||||
|
layers. The highest layer provides ease of use, while lower layers provide
|
||||||
|
additional control and flexibility. The layers are arranged thusly:
|
||||||
|
|
||||||
|
[table
|
||||||
|
[[Level][Read/Write What][Description]]
|
||||||
|
[
|
||||||
|
[[*2]]
|
||||||
|
[
|
||||||
|
message
|
||||||
|
][
|
||||||
|
At the top layer, these functions allow for an entire
|
||||||
|
message to be sent or received. They are designed for
|
||||||
|
ease of use:
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.read.overload2 `read`],
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.write.overload2 `write`],
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.async_read `async_read`], and
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.async_write `async_write`].
|
||||||
|
]
|
||||||
|
][
|
||||||
|
[[*1]]
|
||||||
|
[
|
||||||
|
['partial]
|
||||||
|
][
|
||||||
|
These read functions enable partial message data to be
|
||||||
|
received into a __DynamicBuffer__. They can be configured
|
||||||
|
to perform bounded work:
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.read_some.overload2 `read_some`], and
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.async_read_some.overload1 `async_read_some`].
|
||||||
|
]
|
||||||
|
][
|
||||||
|
[[*0]]
|
||||||
|
[
|
||||||
|
['partial]
|
||||||
|
][
|
||||||
|
At the lowest level these read and write functions enable
|
||||||
|
partial message data to be transacted using a constant or
|
||||||
|
mutable buffer sequence:
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.read_some.overload4 `read_some`],
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.write_some.overload2 `write_some`],
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.async_read_some.overload2 `async_read_some`], and
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.async_write_some `async_write_some`].
|
||||||
|
]
|
||||||
|
]]
|
||||||
|
|
||||||
After the WebSocket handshake is accomplished, callers may send and receive
|
After the WebSocket handshake is accomplished, callers may send and receive
|
||||||
messages using the message oriented interface. This interface requires that
|
messages using the message oriented interface. This interface requires that
|
||||||
all of the buffers representing the message are known ahead of time:
|
all of the buffers representing the message are known ahead of time:
|
||||||
|
@@ -80,22 +80,26 @@ a stream read operation must be active.
|
|||||||
|
|
||||||
[heading Close Frames]
|
[heading Close Frames]
|
||||||
|
|
||||||
The WebSocket protocol defines a procedure and control message for initiating
|
The WebSocket protocol defines a procedure and control message for
|
||||||
a close of the session. Handling of close initiated by the remote end of the
|
initiating a close of the session. In this procedure, a host requests
|
||||||
connection is performed automatically. To manually initiate a close, use
|
the close by sending a
|
||||||
the
|
[@https://tools.ietf.org/html/rfc6455#section-5.5.1 ['close frame]].
|
||||||
[link beast.ref.boost__beast__websocket__stream.close `close`] function:
|
To request a close use a close function such as
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.close.overload2 `close`] or
|
||||||
|
[link beast.ref.boost__beast__websocket__stream.async_close `async_close`]:
|
||||||
|
|
||||||
[ws_snippet_18]
|
[ws_snippet_18]
|
||||||
|
|
||||||
When the remote peer initiates a close by sending a close frame, Beast
|
The close function will send a close frame, read and discard incoming
|
||||||
will handle it for you by causing the next read to return `error::closed`.
|
message data until receiving a close frame, and then shut down the
|
||||||
When this error code is delivered, it indicates to the application that
|
underlying connection before returning.
|
||||||
the WebSocket connection has been closed cleanly, and that the TCP/IP
|
|
||||||
connection has been closed. After initiating a close, it is necessary to
|
When a close frame is received by during a read operation, the implementation
|
||||||
continue reading messages until receiving the error `error::closed`. This
|
will automatically respond with a close frame and then shut down the
|
||||||
is because the remote peer may still be sending message and control frames
|
underlying connection before returning. In this case, the read operation
|
||||||
before it receives and responds to the close frame.
|
will complete with the code
|
||||||
|
[link beast.ref.boost__beast__websocket__error `error::closed`].
|
||||||
|
This indicates to the caller that the connection has been closed cleanly.
|
||||||
|
|
||||||
[important
|
[important
|
||||||
To receive the
|
To receive the
|
||||||
@@ -105,10 +109,10 @@ before it receives and responds to the close frame.
|
|||||||
|
|
||||||
[heading Auto-fragment]
|
[heading Auto-fragment]
|
||||||
|
|
||||||
To ensure timely delivery of control frames, large messages can be broken up
|
To ensure timely delivery of control frames, large outgoing messages can
|
||||||
into smaller sized frames. The automatic fragment option turns on this
|
be broken up into smaller sized frames. The automatic fragment option
|
||||||
feature, and the write buffer size option determines the maximum size of
|
turns on this feature, and the write buffer size option determines the
|
||||||
the fragments:
|
maximum size of the fragments:
|
||||||
|
|
||||||
[ws_snippet_19]
|
[ws_snippet_19]
|
||||||
|
|
||||||
|
66
doc/qbk/06_websocket/7_teardown.qbk
Normal file
66
doc/qbk/06_websocket/7_teardown.qbk
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
[/
|
||||||
|
Copyright (c) 2016-2017 Vinnie Falco (vinnie dot falco at gmail dot com)
|
||||||
|
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||||
|
|
||||||
|
Official repository: https://github.com/boostorg/beast
|
||||||
|
]
|
||||||
|
|
||||||
|
[section Teardown]
|
||||||
|
|
||||||
|
The WebSocket protocol requirements described in rfc6455 section 7.1.1
|
||||||
|
outline an operation described as
|
||||||
|
[@https://tools.ietf.org/html/rfc6455#section-7.1.1 ['Close the WebSocket Connection]].
|
||||||
|
This operation cleanly discards bytes remaining at receiving endpoints
|
||||||
|
and also closes the underlying TCP/IP connection. Orderly shutdowns are
|
||||||
|
always preferred; for TLS or SSL streams, a protocol-level shutdown is
|
||||||
|
desired. This presents a small issue for the
|
||||||
|
[link beast.ref.boost__beast__websocket__stream `stream`]
|
||||||
|
implementation: the stream's `NextLayer` template type requires only
|
||||||
|
__SyncStream__ or __AsyncStream__, but those concepts do not support
|
||||||
|
the operations to shut down the connection.
|
||||||
|
|
||||||
|
To enable the implementation to perform the shutdown components of the
|
||||||
|
close operation, the library exposes two customization points expressed
|
||||||
|
as free functions associated with the next layer type:
|
||||||
|
|
||||||
|
* [link beast.ref.boost__beast__websocket__teardown `teardown`]: Overloads
|
||||||
|
of this function drain and shut down a stream synchronously.
|
||||||
|
|
||||||
|
* [link beast.ref.boost__beast__websocket__teardown `async_teardown`]:
|
||||||
|
Overloads of this function drain and shut down a stream asynchronously.
|
||||||
|
|
||||||
|
The implementation provides suitable overloads of the teardown
|
||||||
|
customization points when websocket streams are instantiated using the
|
||||||
|
Asio types __socket__ or __ssl_stream__ for the next layer. In this
|
||||||
|
case no user action is required. However, when the websocket stream is
|
||||||
|
instantiated for a user-defined type, compile errors will result if the
|
||||||
|
customization points are not provided for the user defined type.
|
||||||
|
Furthermore, user-defined types that wrap one of the Asio objects
|
||||||
|
mentioned earlier may wish to invoke a teardown customization point
|
||||||
|
for the wrapped object. This is how those tasks are accomplished.
|
||||||
|
|
||||||
|
[heading User-defined Teardown]
|
||||||
|
|
||||||
|
To provide overloads of teardown for a user-defined type, simply declare
|
||||||
|
the two free functions with the correct signature, accepting a reference
|
||||||
|
to the user-defined type as the stream parameter:
|
||||||
|
|
||||||
|
[ws_snippet_22]
|
||||||
|
|
||||||
|
When the implementation invokes the asynchronous teardown function, it
|
||||||
|
always uses an invokable completion handler. It is not necessary
|
||||||
|
to specify the return type customization when creating user-defined
|
||||||
|
overloads of `async_teardown`.
|
||||||
|
|
||||||
|
[heading Invoking Teardown]
|
||||||
|
|
||||||
|
To invoke the customization point, first bring the default implementation
|
||||||
|
into scope with a `using` statement. Then call the customization point
|
||||||
|
without namespace qualification, allowing argument-dependent lookup to
|
||||||
|
take effect:
|
||||||
|
|
||||||
|
[ws_snippet_23]
|
||||||
|
|
||||||
|
[endsect]
|
@@ -38,12 +38,11 @@ namespace http {
|
|||||||
fields.
|
fields.
|
||||||
The parser is optimized for the case where the input buffer
|
The parser is optimized for the case where the input buffer
|
||||||
sequence consists of a single contiguous buffer. The
|
sequence consists of a single contiguous buffer. The
|
||||||
@ref beast::flat_buffer class is provided, which guarantees
|
@ref flat_buffer class is provided, which guarantees
|
||||||
that the input sequence of the stream buffer will be represented
|
that the input sequence of the stream buffer will be represented
|
||||||
by exactly one contiguous buffer. To ensure the optimum performance
|
by exactly one contiguous buffer. To ensure the optimum performance
|
||||||
of the parser, use @ref beast::flat_buffer with HTTP algorithms
|
of the parser, use @ref flat_buffer with HTTP algorithms
|
||||||
such as @ref beast::http::read, @ref beast::http::read_some,
|
such as @ref read, @ref read_some, @ref async_read, and @ref async_read_some.
|
||||||
@ref beast::http::async_read, and @ref beast::http::async_read_some.
|
|
||||||
Alternatively, the caller may use custom techniques to ensure that
|
Alternatively, the caller may use custom techniques to ensure that
|
||||||
the structured portion of the HTTP message (header or chunk header)
|
the structured portion of the HTTP message (header or chunk header)
|
||||||
is contained in a linear buffer.
|
is contained in a linear buffer.
|
||||||
|
@@ -232,6 +232,68 @@ void echo(stream<boost::asio::ip::tcp::socket>& ws,
|
|||||||
//]
|
//]
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//[ws_snippet_22
|
||||||
|
|
||||||
|
struct custom_stream
|
||||||
|
{
|
||||||
|
friend
|
||||||
|
void
|
||||||
|
teardown(
|
||||||
|
role_type role,
|
||||||
|
custom_stream& stream,
|
||||||
|
error_code& ec);
|
||||||
|
|
||||||
|
template<class TeardownHandler>
|
||||||
|
friend
|
||||||
|
void
|
||||||
|
async_teardown(
|
||||||
|
role_type role,
|
||||||
|
custom_stream& stream,
|
||||||
|
TeardownHandler&& handler);
|
||||||
|
};
|
||||||
|
|
||||||
|
//]
|
||||||
|
|
||||||
|
//[ws_snippet_23
|
||||||
|
|
||||||
|
template<class NextLayer>
|
||||||
|
struct custom_wrapper
|
||||||
|
{
|
||||||
|
NextLayer next_layer;
|
||||||
|
|
||||||
|
template<class... Args>
|
||||||
|
explicit
|
||||||
|
custom_wrapper(Args&&... args)
|
||||||
|
: next_layer(std::forward<Args>(args)...)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
friend
|
||||||
|
void
|
||||||
|
teardown(
|
||||||
|
role_type role,
|
||||||
|
custom_stream& stream,
|
||||||
|
error_code& ec)
|
||||||
|
{
|
||||||
|
using boost::beast::websocket::teardown;
|
||||||
|
teardown(role, stream.next_layer, ec);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class TeardownHandler>
|
||||||
|
friend
|
||||||
|
void
|
||||||
|
async_teardown(
|
||||||
|
role_type role,
|
||||||
|
custom_stream& stream,
|
||||||
|
TeardownHandler&& handler)
|
||||||
|
{
|
||||||
|
using boost::beast::websocket::async_teardown;
|
||||||
|
async_teardown(role, stream.next_layer, std::forward<TeardownHandler>(handler));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
//]
|
||||||
|
|
||||||
} // doc_ws_snippets
|
} // doc_ws_snippets
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
|
Reference in New Issue
Block a user