Files
beast/test/http/test_parser.hpp
T
Vinnie Falco f47b66179e New HTTP interfaces (API Change):
fix #123
fix #154
fix #265

This completely replaces the HTTP parser used to read and
parse incoming messages. The new version is faster than
the old one, and written in fewer lines. A summary of
changes:

* parse and async_parse renamed to read and async_read

* basic_parser is optimized for linear buffers,
  use flat_streambuf for the best performance with these
  functions:

  - http::read
  - http::read_some
  - http::async_read
  - http::async_read_some

* The overloads of read() and async_read() which take
  just a header have been removed, since they would
  throw away important parse metadata.

* The derived class callbacks for basic_parser have
  been streamlined. All strings passed to callbacks
  are presented in their entirety, instead of being
  provided in pieces.

These changes allow use-cases that were previously
difficult or impossible, such as:

- Efficient relaying

- Late body type commitment

- Expect: 100-continue handling
2017-05-04 18:58:33 -07:00

148 lines
3.0 KiB
C++

//
// Copyright (c) 2013-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)
//
#ifndef BEAST_HTTP_TEST_PARSER_HPP
#define BEAST_HTTP_TEST_PARSER_HPP
#include <beast/http/basic_parser.hpp>
#include <beast/test/fail_counter.hpp>
namespace beast {
namespace http {
template<bool isRequest>
class test_parser
: public basic_parser<isRequest, false,
test_parser<isRequest>>
{
test::fail_counter* fc_ = nullptr;
public:
using mutable_buffers_type =
boost::asio::mutable_buffers_1;
int status = 0;
int version = 0;
std::string method;
std::string path;
std::string reason;
std::string body;
bool got_on_begin = false;
bool got_on_field = false;
bool got_on_header = false;
bool got_on_body = false;
bool got_content_length = false;
bool got_on_prepare = false;
bool got_on_commit = false;
bool got_on_chunk = false;
bool got_on_complete = false;
test_parser() = default;
explicit
test_parser(test::fail_counter& fc)
: fc_(&fc)
{
}
void
on_request(
boost::string_ref const& method_,
boost::string_ref const& path_,
int version_, error_code& ec)
{
method = std::string(
method_.data(), method_.size());
path = std::string(
path_.data(), path_.size());
version = version_;
got_on_begin = true;
if(fc_)
fc_->fail(ec);
}
void
on_response(int status_,
boost::string_ref const& reason_,
int version_, error_code& ec)
{
status = status_;
reason = std::string(
reason_.data(), reason_.size());
version = version_;
got_on_begin = true;
if(fc_)
fc_->fail(ec);
}
void
on_field(boost::string_ref const&,
boost::string_ref const&,
error_code& ec)
{
got_on_field = true;
if(fc_)
fc_->fail(ec);
}
void
on_header(error_code& ec)
{
got_on_header = true;
if(fc_)
fc_->fail(ec);
}
void
on_body(error_code& ec)
{
got_on_body = true;
if(fc_)
fc_->fail(ec);
}
void
on_body(std::uint64_t content_length,
error_code& ec)
{
got_on_body = true;
got_content_length = true;
if(fc_)
fc_->fail(ec);
}
void
on_data(boost::string_ref const& s,
error_code& ec)
{
body.append(s.data(), s.size());
}
void
on_chunk(std::uint64_t,
boost::string_ref const&,
error_code& ec)
{
got_on_chunk = true;
if(fc_)
fc_->fail(ec);
}
void
on_complete(error_code& ec)
{
got_on_complete = true;
if(fc_)
fc_->fail(ec);
}
};
} // http
} // beast
#endif