28 #ifndef WEBSOCKETPP_TRANSPORT_ASIO_CON_HPP 29 #define WEBSOCKETPP_TRANSPORT_ASIO_CON_HPP 66 template <
typename config>
72 typedef lib::shared_ptr<type>
ptr;
91 typedef lib::shared_ptr<lib::asio::io_service::strand>
strand_ptr;
93 typedef lib::shared_ptr<lib::asio::steady_timer>
timer_ptr;
101 explicit connection(
bool is_server,
const lib::shared_ptr<alog_type> & alog,
const lib::shared_ptr<elog_type> & elog)
102 : m_is_server(is_server)
145 m_tcp_pre_init_handler = h;
174 m_tcp_post_init_handler = h;
193 m_proxy_data = lib::make_shared<proxy_data>();
194 ec = lib::error_code();
218 password, lib::error_code & ec)
226 std::string val =
"Basic "+
base64_encode(username +
":" + password);
227 m_proxy_data->req.replace_header(
"Proxy-Authorization",val);
228 ec = lib::error_code();
256 m_proxy_data->timeout_proxy =
duration;
257 ec = lib::error_code();
296 return m_connection_hdl;
314 timer_ptr new_timer = lib::make_shared<lib::asio::steady_timer>(
320 new_timer->async_wait(m_strand->wrap(lib::bind(
324 lib::placeholders::_1
327 new_timer->async_wait(lib::bind(
331 lib::placeholders::_1
350 lib::asio::error_code
const & ec)
360 callback(lib::error_code());
423 lib::placeholders::_1
441 m_proxy_data->req.set_version(
"HTTP/1.1");
442 m_proxy_data->req.set_method(
"CONNECT");
444 m_proxy_data->req.set_uri(authority);
445 m_proxy_data->req.replace_header(
"Host",authority);
447 return lib::error_code();
461 m_io_service = io_service;
464 m_strand = lib::make_shared<lib::asio::io_service::strand>(
479 if (m_tcp_pre_init_handler) {
480 m_tcp_pre_init_handler(m_connection_hdl);
489 if (!m_proxy.empty()) {
501 timer_ptr post_timer;
511 lib::placeholders::_1
522 lib::placeholders::_1
537 lib::error_code
const & ec)
539 lib::error_code ret_ec;
544 "asio post init timer cancelled");
573 lib::error_code
const & ec)
583 post_timer->cancel();
590 if (m_tcp_post_init_handler) {
591 m_tcp_post_init_handler(m_connection_hdl);
604 "assertion failed: !m_proxy_data in asio::connection::proxy_write");
609 m_proxy_data->write_buf = m_proxy_data->req.raw();
611 m_bufs.push_back(lib::asio::buffer(m_proxy_data->write_buf.data(),
612 m_proxy_data->write_buf.size()));
618 m_proxy_data->timeout_proxy,
623 lib::placeholders::_1
629 lib::asio::async_write(
632 m_strand->wrap(lib::bind(
635 lib::placeholders::_1
639 lib::asio::async_write(
645 lib::placeholders::_1
655 "asio handle_proxy_write timer cancelled");
662 "asio handle_proxy_write timer expired");
669 lib::asio::error_code
const & ec)
673 "asio connection handle_proxy_write");
690 m_proxy_data->timer->cancel();
705 "assertion failed: !m_proxy_data in asio::connection::proxy_read");
706 m_proxy_data->timer->cancel();
712 lib::asio::async_read_until(
714 m_proxy_data->read_buf,
716 m_strand->wrap(lib::bind(
719 lib::placeholders::_1, lib::placeholders::_2
723 lib::asio::async_read_until(
725 m_proxy_data->read_buf,
730 lib::placeholders::_1, lib::placeholders::_2
743 lib::asio::error_code
const & ec,
size_t)
747 "asio connection handle_proxy_read");
761 m_proxy_data->timer->cancel();
765 "asio handle_proxy_read error: "+ec.message());
770 "assertion failed: !m_proxy_data in asio::connection::handle_proxy_read");
775 std::istream input(&m_proxy_data->read_buf);
777 m_proxy_data->res.consume(input);
779 if (!m_proxy_data->res.headers_ready()) {
793 s <<
"Proxy connection error: " 794 << m_proxy_data->res.get_status_code()
796 << m_proxy_data->res.get_status_msg()
812 m_proxy_data.reset();
825 s <<
"asio async_read_at_least: " << num_bytes;
840 lib::asio::async_read(
842 lib::asio::buffer(buf,len),
843 lib::asio::transfer_at_least(num_bytes),
845 m_read_handler_allocator,
849 lib::placeholders::_1, lib::placeholders::_2
854 lib::asio::async_read(
856 lib::asio::buffer(buf,len),
857 lib::asio::transfer_at_least(num_bytes),
859 m_read_handler_allocator,
863 lib::placeholders::_1, lib::placeholders::_2
872 size_t bytes_transferred)
896 handler(tec,bytes_transferred);
901 "handle_async_read called with null read handler");
907 m_bufs.push_back(lib::asio::buffer(buf,len));
910 lib::asio::async_write(
914 m_write_handler_allocator,
918 lib::placeholders::_1, lib::placeholders::_2
923 lib::asio::async_write(
927 m_write_handler_allocator,
931 lib::placeholders::_1, lib::placeholders::_2
940 std::vector<buffer>::const_iterator it;
942 for (it = bufs.begin(); it != bufs.end(); ++it) {
943 m_bufs.push_back(lib::asio::buffer((*it).buf,(*it).len));
947 lib::asio::async_write(
951 m_write_handler_allocator,
955 lib::placeholders::_1, lib::placeholders::_2
960 lib::asio::async_write(
964 m_write_handler_allocator,
968 lib::placeholders::_1, lib::placeholders::_2
993 "handle_async_write called with null write handler");
1005 m_connection_hdl = hdl;
1015 m_io_service->post(m_strand->wrap(handler));
1017 m_io_service->post(handler);
1019 return lib::error_code();
1024 m_io_service->post(m_strand->wrap(handler));
1026 m_io_service->post(handler);
1028 return lib::error_code();
1041 timer_ptr shutdown_timer;
1049 lib::placeholders::_1
1059 lib::placeholders::_1
1071 lib::error_code
const & ec)
1073 lib::error_code ret_ec;
1078 "asio socket shutdown timer cancelled");
1089 "Asio transport socket shutdown timed out");
1095 callback, lib::asio::error_code
const & ec)
1104 shutdown_timer->cancel();
1106 lib::error_code tec;
1108 if (ec == lib::asio::error::not_connected) {
1127 "asio con handle_async_shutdown");
1148 template <
typename error_type>
1149 void log_err(
log::level l,
const char * msg,
const error_type & ec) {
1150 std::stringstream s;
1151 s << msg <<
" error: " << ec <<
" (" << ec.message() <<
")";
1152 m_elog->write(l,s.str());
1156 const bool m_is_server;
1157 lib::shared_ptr<alog_type> m_alog;
1158 lib::shared_ptr<elog_type> m_elog;
1165 std::string write_buf;
1166 lib::asio::streambuf read_buf;
1171 std::string m_proxy;
1172 lib::shared_ptr<proxy_data> m_proxy_data;
1175 io_service_ptr m_io_service;
1176 strand_ptr m_strand;
1179 std::vector<lib::asio::const_buffer> m_bufs;
1182 lib::asio::error_code m_tec;
1185 tcp_init_handler m_tcp_pre_init_handler;
1186 tcp_init_handler m_tcp_post_init_handler;
1197 #endif // WEBSOCKETPP_TRANSPORT_ASIO_CON_HPP static const bool enable_multithreading
void handle_async_shutdown(timer_ptr shutdown_timer, shutdown_handler callback, lib::asio::error_code const &ec)
Asio based endpoint transport component.
static const long timeout_socket_shutdown
config::elog_type elog_type
Type of this transport's error logging policy.
void async_shutdown(socket::shutdown_handler callback)
lib::error_code make_error_code(error::value e)
TLS enabled Asio connection socket component.
socket_type & get_socket()
Retrieve a pointer to the wrapped socket.
void cancel_socket_checked()
Cancel the underlying socket and log any errors.
static lib::error_code translate_ec(ErrorCodeType ec)
Translate any security policy specific information about an error code.
lib::shared_ptr< type > ptr
Type of a shared pointer to this connection socket component.
void async_write(const char *buf, size_t len, write_handler handler)
Initiate a potentially asyncronous write of the given buffer.
lib::asio::error_code cancel_socket()
Cancel all async operations on this socket.
void proxy_write(init_handler callback)
void set_proxy_basic_auth(std::string const &username, std::string const &password, lib::error_code &ec)
Set the basic auth credentials to use (exception free)
void pre_init(init_handler callback)
Pre-initialize security policy.
lib::shared_ptr< type > ptr
std::string get_remote_endpoint() const
Get the remote endpoint address.
lib::asio::io_service * io_service_ptr
Type of a pointer to the Asio io_service being used.
boost::posix_time::time_duration milliseconds(long duration)
connection_hdl get_handle() const
Get the connection handle.
void set_tcp_pre_init_handler(tcp_init_handler h)
Sets the tcp pre init handler.
strand_ptr get_strand()
Get a pointer to this connection's strand.
void set_handle(connection_hdl hdl)
Sets the connection handle.
lib::function< void(lib::error_code const &)> write_handler
The type and signature of the callback passed to the write method.
static level const devel
Low level debugging information (warning: very chatty)
bool is_secure() const
Check whether or not this connection is secure.
lib::weak_ptr< void > connection_hdl
A handle to uniquely identify a connection.
void handle_async_read(read_handler handler, lib::asio::error_code const &ec, size_t bytes_transferred)
socket_con_type::ptr socket_con_ptr
Type of a shared pointer to the socket connection component.
boost::chrono::duration< Rep, Period > duration
request_type::ptr request_ptr
void proxy_read(init_handler callback)
void handle_post_init_timeout(timer_ptr, init_handler callback, lib::error_code const &ec)
Post init timeout callback.
void async_write(std::vector< buffer > const &bufs, write_handler handler)
Initiate a potentially asyncronous write of the given buffers.
lib::function< void()> interrupt_handler
The type and signature of the callback passed to the interrupt method.
lib::error_code get_ec() const
lib::shared_ptr< type > ptr
Type of a shared pointer to this connection transport component.
lib::function< void(lib::error_code const &, size_t)> read_handler
The type and signature of the callback passed to the read method.
std::string base64_encode(unsigned char const *input, size_t len)
Encode a char buffer into a base64 string.
lib::asio::error_code get_transport_ec() const
Get the internal transport error code for a closed/failed connection.
underlying transport pass through
void init(init_handler callback)
Initialize transport for reading.
socket_type::next_layer_type & get_next_layer()
Retrieve a pointer to the layer below the ssl stream.
void post_init(init_handler callback)
Stores, parses, and manipulates HTTP responses.
void handle_pre_init(init_handler callback, lib::error_code const &ec)
void handle_async_shutdown_timeout(timer_ptr, init_handler callback, lib::error_code const &ec)
Async shutdown timeout handler.
void handle_async_write(write_handler handler, lib::asio::error_code const &ec, size_t)
Async write callback.
void set_tcp_post_init_handler(tcp_init_handler h)
Sets the tcp post init handler.
static level const devel
Development messages (warning: very chatty)
void handle_timer(timer_ptr, timer_handler callback, lib::asio::error_code const &ec)
Timer callback.
std::string get_remote_endpoint(lib::error_code &ec) const
Get the remote endpoint address.
timer_ptr set_timer(long duration, timer_handler callback)
Call back a function after a period of time.
lib::shared_ptr< type > ptr
void set_proxy(std::string const &uri, lib::error_code &ec)
Set the proxy to connect through (exception free)
config::alog_type alog_type
Type of this transport's access logging policy.
lib::shared_ptr< lib::asio::io_service::strand > strand_ptr
Type of a pointer to the Asio io_service::strand being used.
void set_uri(uri_ptr u)
Set hostname hook.
lib::function< void()> dispatch_handler
The type and signature of the callback passed to the dispatch method.
void handle_proxy_read(init_handler callback, lib::asio::error_code const &ec, size_t)
Proxy read callback.
The connection was in the wrong state for this operation.
lib::error_code interrupt(interrupt_handler handler)
Trigger the on_interrupt handler.
lib::error_code dispatch(dispatch_handler handler)
static level const info
Information about minor configuration problems or additional information about other warnings...
void set_proxy_timeout(long duration, lib::error_code &ec)
Set the proxy timeout duration (exception free)
ptr get_shared()
Get a shared pointer to this component.
lib::function< void(lib::error_code const &)> timer_handler
The type and signature of the callback passed to the read method.
there was an error in the underlying transport library
lib::function< void(lib::error_code const &)> shutdown_handler
The type and signature of the callback passed to the shutdown method.
Namespace for the WebSocket++ project.
config::request_type request_type
void set_proxy_timeout(long duration)
Set the proxy timeout duration (exception)
lib::function< void(lib::error_code const &)> init_handler
The type and signature of the callback passed to the init hook.
lib::error_code init_asio(io_service_ptr service, strand_ptr strand, bool is_server)
Perform one time initializations.
static const long timeout_proxy
config::response_type response_type
Asio based connection transport component.
static const long timeout_socket_post_init
custom_alloc_handler< Handler > make_custom_alloc_handler(handler_allocator &a, Handler h)
lib::shared_ptr< uri > uri_ptr
Pointer to a URI.
lib::shared_ptr< lib::asio::steady_timer > timer_ptr
Type of a pointer to the Asio timer class.
The connection to the requested proxy server failed.
ptr get_shared()
Get a shared pointer to this component.
void handle_proxy_write(init_handler callback, lib::asio::error_code const &ec)
connection< config > type
Type of this connection transport component.
std::string const & get_proxy() const
void post_init(init_handler callback)
Post-initialize security policy.
lib::function< void(connection_hdl)> tcp_init_handler
void handle_post_init(timer_ptr post_timer, init_handler callback, lib::error_code const &ec)
Post init timeout callback.
void async_shutdown(shutdown_handler callback)
close and clean up the underlying socket
Stores, parses, and manipulates HTTP requests.
response_type::ptr response_ptr
lib::error_code proxy_init(std::string const &authority)
initialize the proxy buffers and http parsers
lib::error_code init_asio(io_service_ptr io_service)
Finish constructing the transport.
uint32_t level
Type of a channel package.
lib::error_code make_error_code(error::value e)
config::socket_type::socket_con_type socket_con_type
Type of the socket connection component.
void set_proxy(std::string const &uri)
Set the proxy to connect through (exception)
void async_read_at_least(size_t num_bytes, char *buf, size_t len, read_handler handler)
read at least num_bytes bytes into buf and then call handler.
void set_tcp_init_handler(tcp_init_handler h)
Sets the tcp pre init handler (deprecated)
Stub logger that ignores all input.
static level const library
Information about unusual system states or other minor internal library problems, less chatty than de...
connection(bool is_server, const lib::shared_ptr< alog_type > &alog, const lib::shared_ptr< elog_type > &elog)
void set_handle(connection_hdl hdl)
Set Connection Handle.
Catch-all error for transport policy errors that don't fit in other categories.
static level const warn
Information about important problems not severe enough to terminate connections.
void set_uri(uri_ptr u)
Set uri hook.
void handle_proxy_timeout(init_handler callback, lib::error_code const &ec)
void set_proxy_basic_auth(std::string const &username, std::string const &password)
Set the basic auth credentials to use (exception)