reformat Server/RequestHandler according to guideline

This commit is contained in:
Dennis Luxen 2014-05-07 17:08:30 +02:00
parent 3f4c4d675b
commit bd316e7e98
2 changed files with 98 additions and 158 deletions

View File

@ -38,118 +38,81 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include <string>
#include <vector>
namespace http {
namespace http
{
Connection::Connection(
boost::asio::io_service& io_service,
RequestHandler& handler
) :
strand(io_service),
TCP_socket(io_service),
request_handler(handler),
request_parser(new RequestParser())
{ }
Connection::~Connection() {
delete request_parser;
Connection::Connection(boost::asio::io_service &io_service, RequestHandler &handler)
: strand(io_service), TCP_socket(io_service), request_handler(handler),
request_parser(new RequestParser())
{
}
boost::asio::ip::tcp::socket& Connection::socket() {
return TCP_socket;
}
Connection::~Connection() { delete request_parser; }
boost::asio::ip::tcp::socket &Connection::socket() { return TCP_socket; }
/// Start the first asynchronous operation for the connection.
void Connection::start() {
void Connection::start()
{
TCP_socket.async_read_some(
boost::asio::buffer(incoming_data_buffer),
strand.wrap( boost::bind(
&Connection::handle_read,
this->shared_from_this(),
boost::asio::placeholders::error,
boost::asio::placeholders::bytes_transferred)
)
);
strand.wrap(boost::bind(&Connection::handle_read,
this->shared_from_this(),
boost::asio::placeholders::error,
boost::asio::placeholders::bytes_transferred)));
}
void Connection::handle_read(
const boost::system::error_code& e,
std::size_t bytes_transferred
) {
if( !e ) {
void Connection::handle_read(const boost::system::error_code &e, std::size_t bytes_transferred)
{
if (!e)
{
CompressionType compression_type(noCompression);
boost::tribool result;
boost::tie(result, boost::tuples::ignore) = request_parser->Parse(
request,
incoming_data_buffer.data(),
incoming_data_buffer.data() + bytes_transferred,
&compression_type
);
boost::tie(result, boost::tuples::ignore) =
request_parser->Parse(request,
incoming_data_buffer.data(),
incoming_data_buffer.data() + bytes_transferred,
&compression_type);
if( result ) {
if (result)
{
request.endpoint = TCP_socket.remote_endpoint().address();
request_handler.handle_request(request, reply);
Header compression_header;
std::vector<char> compressed_output;
std::vector<boost::asio::const_buffer> output_buffer;
switch(compression_type) {
switch (compression_type)
{
case deflateRFC1951:
compression_header.name = "Content-Encoding";
compression_header.value = "deflate";
reply.headers.insert(
reply.headers.begin(),
compression_header
);
compressBufferCollection(
reply.content,
compression_type,
compressed_output
);
reply.headers.insert(reply.headers.begin(), compression_header);
compressBufferCollection(reply.content, compression_type, compressed_output);
reply.setSize(compressed_output.size());
output_buffer = reply.HeaderstoBuffers();
output_buffer.push_back(
boost::asio::buffer(compressed_output)
);
output_buffer.push_back(boost::asio::buffer(compressed_output));
boost::asio::async_write(
TCP_socket,
output_buffer,
strand.wrap(
boost::bind(
&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error
)
)
);
strand.wrap(boost::bind(&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error)));
break;
case gzipRFC1952:
compression_header.name = "Content-Encoding";
compression_header.value = "gzip";
reply.headers.insert(
reply.headers.begin(),
compression_header
);
compressBufferCollection(
reply.content,
compression_type,
compressed_output
);
reply.headers.insert(reply.headers.begin(), compression_header);
compressBufferCollection(reply.content, compression_type, compressed_output);
reply.setSize(compressed_output.size());
output_buffer = reply.HeaderstoBuffers();
output_buffer.push_back(
boost::asio::buffer(compressed_output)
);
output_buffer.push_back(boost::asio::buffer(compressed_output));
boost::asio::async_write(
TCP_socket,
output_buffer,
strand.wrap(
boost::bind(
&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error
)
)
);
strand.wrap(boost::bind(&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error)));
break;
case noCompression:
reply.SetUncompressedSize();
@ -157,81 +120,65 @@ void Connection::handle_read(
boost::asio::async_write(
TCP_socket,
output_buffer,
strand.wrap(
boost::bind(
&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error
)
)
);
strand.wrap(boost::bind(&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error)));
break;
}
} else if (!result) {
}
else if (!result)
{
reply = Reply::StockReply(Reply::badRequest);
boost::asio::async_write(
TCP_socket,
reply.toBuffers(),
strand.wrap(
boost::bind(
&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error
)
)
);
} else {
boost::asio::async_write(TCP_socket,
reply.toBuffers(),
strand.wrap(boost::bind(&Connection::handle_write,
this->shared_from_this(),
boost::asio::placeholders::error)));
}
else
{
TCP_socket.async_read_some(
boost::asio::buffer(incoming_data_buffer),
strand.wrap(
boost::bind(
&Connection::handle_read,
this->shared_from_this(),
boost::asio::placeholders::error,
boost::asio::placeholders::bytes_transferred
)
)
);
strand.wrap(boost::bind(&Connection::handle_read,
this->shared_from_this(),
boost::asio::placeholders::error,
boost::asio::placeholders::bytes_transferred)));
}
}
}
/// Handle completion of a write operation.
void Connection::handle_write(const boost::system::error_code& e) {
if (!e) {
void Connection::handle_write(const boost::system::error_code &e)
{
if (!e)
{
// Initiate graceful connection closure.
boost::system::error_code ignoredEC;
TCP_socket.shutdown(
boost::asio::ip::tcp::socket::shutdown_both,
ignoredEC
);
TCP_socket.shutdown(boost::asio::ip::tcp::socket::shutdown_both, ignoredEC);
}
}
void Connection::compressBufferCollection(
std::vector<std::string> uncompressed_data,
CompressionType compression_type,
std::vector<char> & compressed_data
) {
void Connection::compressBufferCollection(std::vector<std::string> uncompressed_data,
CompressionType compression_type,
std::vector<char> &compressed_data)
{
boost::iostreams::gzip_params compression_parameters;
compression_parameters.level = boost::iostreams::zlib::best_speed;
if ( deflateRFC1951 == compression_type ) {
if (deflateRFC1951 == compression_type)
{
compression_parameters.noheader = true;
}
BOOST_ASSERT( compressed_data.empty() );
BOOST_ASSERT(compressed_data.empty());
boost::iostreams::filtering_ostream compressing_stream;
compressing_stream.push(
boost::iostreams::gzip_compressor(compression_parameters)
);
compressing_stream.push(
boost::iostreams::back_inserter(compressed_data)
);
compressing_stream.push(boost::iostreams::gzip_compressor(compression_parameters));
compressing_stream.push(boost::iostreams::back_inserter(compressed_data));
for ( const std::string & line : uncompressed_data) {
for (const std::string &line : uncompressed_data)
{
compressing_stream << line;
}

View File

@ -43,48 +43,41 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
class RequestHandler;
namespace http {
namespace http
{
class RequestParser;
/// Represents a single connection from a client.
class Connection : public boost::enable_shared_from_this<Connection>
class Connection : public boost::enable_shared_from_this<Connection>
{
public:
explicit Connection(
boost::asio::io_service& io_service,
RequestHandler& handler
);
Connection(const Connection &) = delete;
~Connection();
public:
explicit Connection(boost::asio::io_service &io_service, RequestHandler &handler);
Connection(const Connection &) = delete;
~Connection();
boost::asio::ip::tcp::socket& socket();
boost::asio::ip::tcp::socket &socket();
/// Start the first asynchronous operation for the connection.
void start();
/// Start the first asynchronous operation for the connection.
void start();
private:
void handle_read(
const boost::system::error_code& e,
std::size_t bytes_transferred
);
private:
void handle_read(const boost::system::error_code &e, std::size_t bytes_transferred);
/// Handle completion of a write operation.
void handle_write(const boost::system::error_code& e);
/// Handle completion of a write operation.
void handle_write(const boost::system::error_code &e);
void compressBufferCollection(
std::vector<std::string> uncompressed_data,
CompressionType compression_type,
std::vector<char> & compressed_data
);
void compressBufferCollection(std::vector<std::string> uncompressed_data,
CompressionType compression_type,
std::vector<char> &compressed_data);
boost::asio::io_service::strand strand;
boost::asio::ip::tcp::socket TCP_socket;
RequestHandler& request_handler;
boost::array<char, 8192> incoming_data_buffer;
Request request;
RequestParser * request_parser;
Reply reply;
boost::asio::io_service::strand strand;
boost::asio::ip::tcp::socket TCP_socket;
RequestHandler &request_handler;
boost::array<char, 8192> incoming_data_buffer;
Request request;
RequestParser *request_parser;
Reply reply;
};
} // namespace http