diff --git a/CMakeLists.txt b/CMakeLists.txt index 3224701..3f9dd6d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -7,7 +7,10 @@ set(CMAKE_CXX_STANDARD_REQUIRED True) set(BUILD_SHARED_LIBS OFF) -add_executable(Application src/main.cpp) +include_directories(${PROJECT_SOURCE_DIR}/includes) +add_executable(Application src/main.cpp + src/tcp_connection.cpp +) find_package(Boost REQUIRED COMPONENTS filesystem system) diff --git a/includes/tcp_connection.hpp b/includes/tcp_connection.hpp new file mode 100644 index 0000000..2b17831 --- /dev/null +++ b/includes/tcp_connection.hpp @@ -0,0 +1,29 @@ +#ifndef TCP_CONNECTION_HPP +#define TCP_CONNECTION_HPP + +#include +#include +#include + +using namespace boost; +using namespace std; + +class tcp_connection : public std::enable_shared_from_this { +public: + typedef std::shared_ptr pointer; + + static pointer create(asio::io_context& io_context); + asio::ip::tcp::socket& socket(); + void handle(); + +private: + asio::ip::tcp::socket socket_; + asio::streambuf buffer_; + + explicit tcp_connection(asio::io_context& io_context); + + void handle_read(const system::error_code& error, size_t bytes_transferred); + void handle_write(const system::error_code& error, size_t bytes_transferred); +}; + +#endif \ No newline at end of file diff --git a/src/main.cpp b/src/main.cpp index c38a2c3..c201c70 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,52 +1,8 @@ +#include "../includes/tcp_connection.hpp" #include #include #include -class tcp_connection : public std::enable_shared_from_this { - public: - typedef std::shared_ptr pointer; - - static pointer create(boost::asio::io_context& io_context) { - return pointer(new tcp_connection(io_context)); - } - - boost::asio::ip::tcp::socket& socket() { - return socket_; - } - - void start() { - boost::asio::async_read_until(socket_, buffer_, "\r\n\r\n", - std::bind(&tcp_connection::handle_read, shared_from_this(), - boost::asio::placeholders::error, - boost::asio::placeholders::bytes_transferred)); - } - - private: - boost::asio::ip::tcp::socket socket_; - boost::asio::streambuf buffer_; - - explicit tcp_connection(boost::asio::io_context& io_context) : socket_(io_context) {} - - void handle_read(const boost::system::error_code& error, std::size_t bytes_transferred) { - if (!error) { - std::istream request_stream(&buffer_); - std::string request_line; - std::getline(request_stream, request_line); - - std::cout << "Received HTTP request line: " << request_line << std::endl; - - std::string header; - while (std::getline(request_stream, header) && header != "\r") { - std::cout << "Header: " << header << std::endl; - } - } - else { - std::cerr << "Error on receiving request: " << error.message() << std::endl; - } - } - -}; - class tcp_server { public: explicit tcp_server(boost::asio::io_context& io_context, const int port): io_context_(io_context), acceptor_(io_context, boost::asio::ip::tcp::endpoint(boost::asio::ip::tcp::v4(), port)) { @@ -65,7 +21,7 @@ class tcp_server { void handle_accept(tcp_connection::pointer& new_connection, const boost::system::error_code& error) { if (!error) { - new_connection->start(); + new_connection->handle(); } start_accept(); } diff --git a/src/tcp_connection.cpp b/src/tcp_connection.cpp new file mode 100644 index 0000000..8a7d3bc --- /dev/null +++ b/src/tcp_connection.cpp @@ -0,0 +1,57 @@ +#include "../includes/tcp_connection.hpp" +#include +#include +#include +#include +#include + +tcp_connection::tcp_connection(asio::io_context& io_context) + : socket_(io_context) {} + +tcp_connection::pointer tcp_connection::create(asio::io_context& io_context) { + return pointer(new tcp_connection(io_context)); +} + +asio::ip::tcp::socket& tcp_connection::socket() { + return socket_; +} + +void tcp_connection::handle() { + asio::async_read_until(socket_, buffer_, "\r\n", + bind(&tcp_connection::handle_read, + shared_from_this(), + asio::placeholders::error, + asio::placeholders::bytes_transferred) + ); +} + +void tcp_connection::handle_read(const boost::system::error_code& error, size_t bytes_transferred) { + if (!error) { + // std::istream request_stream(&buffer_); + // std::string request_line; + // std::getline(request_stream, request_line); + + // auto parsed_data = request_parser_.parse(request_line); + // string response = response_handler_.handle(parsed_data); + + std::string response = "HTTP/1.1 200 OK\r\nContent-Length: 13\r\n\r\nHello, world!"; + auto data = asio::buffer(response); + + asio::async_write(socket_, data, + bind(&tcp_connection::handle_write, + shared_from_this(), + asio::placeholders::error, + asio::placeholders::bytes_transferred) + ); + } else { + std::cerr << "Error during read: " << error.message() << std::endl; + } +} + +void tcp_connection::handle_write(const system::error_code& error, size_t bytes_transferred) { + if (error) { + std::cerr << "Error during write: " << error.message() << std::endl; + } else { + std::cout << "Successfully sent " << bytes_transferred << " bytes." << std::endl; + } +}