http_client scheduler::get_http_client(std::function<void(int, int, std::map<std::string, std::string>&, char*, size_t)> f) { auto sch_impl = std::dynamic_pointer_cast<scheduler_impl>(m_impl); auto& impl = sch_impl->m_util_impls[HTTP_CLI]; if (!impl) { auto http_impl = std::make_shared<http_impl_t<tcp_client_impl>>(NORM_TRANS); http_impl->m_util.m_sch = this; http_impl->m_util.m_app_prt = PRT_HTTP; http_impl->m_util.m_protocol_hook = [this](int fd, char* data, size_t len) { auto this_sch_impl = std::dynamic_pointer_cast<scheduler_impl>(m_impl); if (fd < 0 || fd >= this_sch_impl->m_ev_array.size() || !this_sch_impl->m_ev_array[fd]) return -(int)len; auto conn = std::dynamic_pointer_cast<http_conn_t<tcp_client_conn>>(this_sch_impl->m_ev_array[fd]); return http_parser(true, conn, data, len); }; http_impl->m_util.m_f = [this](int fd, const std::string& ip_addr, uint16_t port, char *data, size_t len) { auto this_sch_impl = std::dynamic_pointer_cast<scheduler_impl>(m_impl); auto& this_http_cli = this_sch_impl->m_util_impls[HTTP_CLI]; auto this_http_impl = std::dynamic_pointer_cast<http_impl_t<tcp_client_impl>>(this_http_cli); tcp_callback_for_http<std::shared_ptr<http_impl_t<tcp_client_impl>>, tcp_client_conn>( true, this_http_impl, fd, data, len); }; http_impl->m_http_cli = std::move(f); //保存回调函数 impl = http_impl; auto ctl = get_sigctl(); //基于tcp_client::connect接口的连接操作在遇到名字解析时将发生协程的切换操作 ctl.add_sig(SIGRTMIN+14, std::bind(&http_impl_t<tcp_client_impl>::name_resolve_callback, http_impl.get(), _1, _2)); } http_client obj; obj.m_impl = impl; return obj; }
std::size_t message::read(std::istream& in, boost::system::error_code& ec, bool headers_only, std::size_t max_content_length) { http::parser http_parser(dynamic_cast<http::request*>(this) != NULL); http_parser.parse_headers_only(headers_only); http_parser.set_max_content_length(max_content_length); return read(in, ec, http_parser); }
http_server scheduler::get_http_server(int port, std::function<void(int, const std::string&, const std::string&, std::map<std::string, std::string>&, char*, size_t)> f) { auto sch_impl = std::dynamic_pointer_cast<scheduler_impl>(m_impl); auto& impl = sch_impl->m_util_impls[HTTP_SVR]; if (!impl) { SOCK_TYPE type = (port >= 0) ? NORM_TRANS : UNIX_DOMAIN; auto http_impl = std::make_shared<http_impl_t<tcp_server_impl>>(type); //创建tcp服务端的监听套接字,允许接收任意ip地址发送的服务请求,监听请求的端口为port http_impl->fd = http_impl->conn_sock.create(PRT_TCP, USR_SERVER, nullptr, (uint16_t)port); if (__glibc_likely(http_impl->fd > 0)) { http_impl->m_util.m_app_prt = PRT_HTTP; http_impl->m_util.m_sch = this; http_impl->m_util.m_protocol_hook = [this](int fd, char* data, size_t len) { auto this_sch_impl = std::dynamic_pointer_cast<scheduler_impl>(m_impl); if (fd < 0 || fd >= this_sch_impl->m_ev_array.size() || !this_sch_impl->m_ev_array[fd]) return -(int)len; auto conn = std::dynamic_pointer_cast<http_conn_t<tcp_server_conn>>(this_sch_impl->m_ev_array[fd]); return http_parser(false, conn, data, len); }; http_impl->m_util.m_f = [this](int fd, const std::string& ip_addr, uint16_t port, char *data, size_t len) { auto this_sch_impl = std::dynamic_pointer_cast<scheduler_impl>(m_impl); auto& this_http_svr = this_sch_impl->m_util_impls[HTTP_SVR]; auto this_http_impl = std::dynamic_pointer_cast<http_impl_t<tcp_server_impl>>(this_http_svr); tcp_callback_for_http<std::shared_ptr<http_impl_t<tcp_server_impl>>, tcp_server_conn>( false, this_http_impl, fd, data, len); }; http_impl->m_http_svr = std::move(f); http_impl->sch_impl = sch_impl; http_impl->f = std::bind(&http_impl_t<tcp_server_impl>::tcp_server_callback, http_impl.get(), _1); sch_impl->add_event(http_impl); impl = http_impl; } } http_server obj; obj.m_impl = impl; return obj; }