diff --git a/Servers/WebServer/Client.cpp b/Servers/WebServer/Client.cpp index 0114d19559..cd1984478d 100644 --- a/Servers/WebServer/Client.cpp +++ b/Servers/WebServer/Client.cpp @@ -28,6 +28,7 @@ #include #include #include +#include #include #include #include @@ -79,22 +80,37 @@ void Client::handle_request(ByteBuffer raw_request) return; } - FileSystemPath canonical_path(request.resource()); - dbg() << "Requested canonical path: '" << canonical_path.string() << "'"; + auto requested_path = canonicalized_path(request.resource()); + dbg() << "Canonical requested path: '" << requested_path << "'"; StringBuilder path_builder; path_builder.append("/www/"); - path_builder.append(canonical_path.string()); + path_builder.append(requested_path); + auto real_path = path_builder.to_string(); - if (Core::File::is_directory(path_builder.to_string())) - path_builder.append("/index.html"); + if (Core::File::is_directory(real_path)) { + StringBuilder index_html_path_builder; + index_html_path_builder.append(real_path); + index_html_path_builder.append("/index.html"); + auto index_html_path = index_html_path_builder.to_string(); + if (!Core::File::exists(index_html_path)) { + handle_directory_listing(requested_path, real_path, request); + return; + } + real_path = index_html_path; + } - auto file = Core::File::construct(path_builder.to_string()); + auto file = Core::File::construct(real_path); if (!file->open(Core::File::ReadOnly)) { send_error_response(404, "Not found, bro!", request); return; } + send_response(file->read_all(), request); +} + +void Client::send_response(StringView response, const Core::HttpRequest& request) +{ StringBuilder builder; builder.append("HTTP/1.0 200 OK\r\n"); builder.append("Server: WebServer (SerenityOS)\r\n"); @@ -102,11 +118,44 @@ void Client::handle_request(ByteBuffer raw_request) builder.append("\r\n"); m_socket->write(builder.to_string()); - m_socket->write(file->read_all()); + m_socket->write(response); log_response(200, request); } +void Client::handle_directory_listing(const String& requested_path, const String& real_path, const Core::HttpRequest& request) +{ + StringBuilder builder; + + builder.append("\n"); + builder.append("\n"); + builder.append("Index of "); + builder.append(requested_path); + builder.append("\n"); + builder.append("\n"); + builder.append("

Index of "); + builder.append(requested_path); + builder.append("

\n"); + builder.append("\n"); + builder.append("\n"); + builder.append("\n"); + + send_response(builder.to_string(), request); +} + void Client::send_error_response(unsigned code, const StringView& message, const Core::HttpRequest& request) { StringBuilder builder; diff --git a/Servers/WebServer/Client.h b/Servers/WebServer/Client.h index aa57b17bba..9b0061b133 100644 --- a/Servers/WebServer/Client.h +++ b/Servers/WebServer/Client.h @@ -44,9 +44,11 @@ private: Client(NonnullRefPtr, Core::Object* parent); void handle_request(ByteBuffer); + void send_response(StringView, const Core::HttpRequest&); void send_error_response(unsigned code, const StringView& message, const Core::HttpRequest&); void die(); void log_response(unsigned code, const Core::HttpRequest&); + void handle_directory_listing(const String& requested_path, const String& real_path, const Core::HttpRequest&); NonnullRefPtr m_socket; };