From 342abdf4c95942ef329ebf9de3aa4f27ebfb12bf Mon Sep 17 00:00:00 2001 From: PythonGermany <97847597+PythonGermany@users.noreply.github.com> Date: Tue, 29 Oct 2024 19:36:18 +0100 Subject: [PATCH] Add server_tokens config option --- README.md | 25 +++++++++++++++++++++---- conf/sites-available/config_test.conf | 4 +++- include/config/Config.hpp | 2 ++ include/http/VirtualHost.hpp | 6 +++++- include/webserv.hpp | 4 +++- src/http/Http.cpp | 7 ++++--- src/http/VirtualHost.cpp | 19 ++++++++++++++++--- 7 files changed, 54 insertions(+), 13 deletions(-) diff --git a/README.md b/README.md index 21b16a3..1a1dfc5 100644 --- a/README.md +++ b/README.md @@ -89,7 +89,7 @@ The configuration file is used to define the configuration of the webserver. It | Config type | Options | | --- | --- | | Configuration file context | [http](#http) / [location](#location) / [server](#server) | -| Configuration file directives | [access_log](#access_log) / [alias](#alias) / [allow](#allow) / [autoindex](#autoindex) / [cgi](#cgi) / [cgi_timeout](#cgi_timeout) / [client_timeout](#client_timout) / [error_log](#error_log) / [error_page](#error_page) / [include](#include) / [index](#index) / [listen](#listen) / [log_level](#log_level) / [log_to_terminal](#log_to_terminal) / [max_client_body_size](#max_client_body_size) / [redirect](#redirect) / [root](#root) / [server_name](#server_name) / [type](#type) | +| Configuration file directives | [access_log](#access_log) / [alias](#alias) / [allow](#allow) / [autoindex](#autoindex) / [cgi](#cgi) / [cgi_timeout](#cgi_timeout) / [client_timeout](#client_timout) / [error_log](#error_log) / [error_page](#error_page) / [include](#include) / [index](#index) / [listen](#listen) / [log_level](#log_level) / [log_to_terminal](#log_to_terminal) / [max_client_body_size](#max_client_body_size) / [redirect](#redirect) / [root](#root) / [server_name](#server_name) / [server_tokens](#server_tokens) / [type](#type) | ## Contexts @@ -110,13 +110,15 @@ http { log_to_terminal [on|off]; log_level LEVEL; + server_tokens [on|off]; + server { [directives] } } ``` Root context. It contains the global configuration of the webserver. -**Allowed tokens:** [access_log](#access_log) / [cgi_timeout](#cgi_timeout) / [client_timeout](#client_timout)/ [error_log](#error_log) / [include](#include) / [log_level](#log_level) / [log_to_terminal](#log_to_terminal) / [server](#server) / [types](#types) +**Allowed tokens:** [access_log](#access_log) / [cgi_timeout](#cgi_timeout) / [client_timeout](#client_timout)/ [error_log](#error_log) / [include](#include) / [log_level](#log_level) / [log_to_terminal](#log_to_terminal) / [server](#server) / [server_tokens](#server_tokens) / [types](#types) ### Types ```nginx @@ -130,6 +132,8 @@ Types context. It contains the mime types of the server. The file [mime.types](c ### Server ```nginx server { + server_tokens [on|off]; + listen HOST:PORT; server_name NAME [NAME ...]; root PATH; @@ -147,7 +151,7 @@ server { } ``` Virtual server context. It contains the configuration of a virtual server. -**Allowed tokens:** [allow](#allow) / [autoindex](#autoindex) / [cgi](#cgi) / [error_page](#error_page) / [index](#index) / [listen](#listen) / [location](#location) / [max_client_body_size](#max_client_body_size) / [root](#root) / [server_name](#server_name) +**Allowed tokens:** [allow](#allow) / [autoindex](#autoindex) / [cgi](#cgi) / [error_page](#error_page) / [index](#index) / [listen](#listen) / [location](#location) / [max_client_body_size](#max_client_body_size) / [root](#root) / [server_name](#server_name) / [server_tokens](#server_tokens) ### Location ```nginx @@ -303,6 +307,13 @@ server_name NAME [NAME ...]; Sets the server names. **Allowed in:** [Server](#server) +### server_tokens +``` +server_tokens [on|off]; +``` +Enables or disables emitting server version in error messages and in the Server response header field. +**Allowed in:** [Http](#http) / [Server](#server) + ### type ```nginx type MIME_TYPE EXTENSION [EXTENSION ...]; @@ -343,21 +354,27 @@ http { # File -> /etc/webserv/sites-enabled/server.conf server { listen 8080; + + server_tokens on; + root /var/www/html; index index.html index.htm; autoindex on; + max_client_body_size 1m; allow GET HEAD OPTIONS; error_page 404 /404.html; + cgi php /usr/bin/php-cgi; location /example { alias /www; # Request: GET /example/file -> ROOT/www/file index example.html; + allow GET HEAD OPTIONS PUT DELETE; autoindex off; } - location /redirect { + location /search { redirect https://www.duckduckgo.com; } } diff --git a/conf/sites-available/config_test.conf b/conf/sites-available/config_test.conf index 44fae51..5a97f2d 100644 --- a/conf/sites-available/config_test.conf +++ b/conf/sites-available/config_test.conf @@ -6,6 +6,8 @@ server { allow GET HEAD OPTIONS; + server_tokens on; + index lol😀.html; autoindex on; @@ -66,4 +68,4 @@ server { cgi py /usr/bin/python3; cgi php /usr/bin/php-cgi; } -} \ No newline at end of file +} diff --git a/include/config/Config.hpp b/include/config/Config.hpp index 71628aa..9dd1ef7 100644 --- a/include/config/Config.hpp +++ b/include/config/Config.hpp @@ -53,6 +53,7 @@ const token_t tokens_g[] = { {"log_level", "http", false, 0, 1, 1, 1, isLogLevel}, {"log_to_terminal", "http", false, 0, 1, 1, 1, isBoolean}, {"server", "http", true, 1, static_cast(-1), 0, 0, NULL}, + {"server_tokens", "http", false, 0, 1, 1, 1, isBoolean}, {"types", "http", true, 1, 1, 0, 0, NULL}, // Mime type context @@ -72,6 +73,7 @@ const token_t tokens_g[] = { {"root", "server", false, 1, 1, 1, 1, NULL}, {"server_name", "server", false, 0, static_cast(-1), 1, static_cast(-1), NULL}, + {"server_tokens", "server", false, 0, 1, 1, 1, isBoolean}, {"max_client_head_size", "server", false, 0, 1, 1, 1, isMemorySize}, {"max_client_body_size", "server", false, 0, 1, 1, 1, isMemorySize}, diff --git a/include/http/VirtualHost.hpp b/include/http/VirtualHost.hpp index 1eb3074..7cd5ebe 100644 --- a/include/http/VirtualHost.hpp +++ b/include/http/VirtualHost.hpp @@ -13,6 +13,7 @@ class VirtualHost { static std::vector _virtualHosts; static std::map _mimeTypes; Context _context; + std::string _externalServerId; std::set
_resolvedListenDirective; public: @@ -25,7 +26,6 @@ class VirtualHost { // Setters/Adders static void add(const VirtualHost &virtualHost); static void setMimeTypes(std::map &mimeTypes); - void setContext(const Context &context); // Getters static std::vector &getVirtualHosts(); @@ -33,9 +33,13 @@ class VirtualHost { std::string const &getAddress(); std::set
const &getResolvedAddress() const; Context &getContext(); + std::string const &getExternalServerId() const; static VirtualHost *matchVirtualHost(Address &address, std::string host); Context *matchLocation(const std::string &uri); + + private: + void setExternalServerId(); }; #endif diff --git a/include/webserv.hpp b/include/webserv.hpp index 1c6566c..658b3e9 100644 --- a/include/webserv.hpp +++ b/include/webserv.hpp @@ -1,7 +1,9 @@ #ifndef WEBSERV_HPP #define WEBSERV_HPP +#define WEBSERV_NAME "webserv" #define WEBSERV_VERSION "0.0.2" -#define WEBSERV_ID "webserv/" WEBSERV_VERSION + +#define WEBSERV_ID WEBSERV_NAME "/" WEBSERV_VERSION #endif diff --git a/src/http/Http.cpp b/src/http/Http.cpp index a353667..a8191f1 100644 --- a/src/http/Http.cpp +++ b/src/http/Http.cpp @@ -263,7 +263,7 @@ void Http::processCgi(std::string contentLength) { std::vector env; // const values: env.push_back("GATEWAY_INTERFACE=CGI/1.1"); - env.push_back("SERVER_SOFTWARE=" WEBSERV_ID); + env.push_back("SERVER_SOFTWARE=" + _virtualHost->getExternalServerId()); env.push_back("SERVER_PROTOCOL=" PROTOCOL "/" HTTP_VERSION); // request specific values: @@ -526,7 +526,8 @@ void Http::checkResourceValidity(const File &file, const std::string &uri) { std::string Http::getDefaultBody(std::string code, std::string reason) const { return "\r\n" + code + " " + reason + "\r\n\r\n

" + code + " " + reason + - "

\r\n
" WEBSERV_ID + "
\r\n
" + + _virtualHost->getExternalServerId() + "
\r\n\r\n\r\n"; } @@ -538,7 +539,7 @@ void Http::sendResponse() { } // Set default header values - _response.setHeader("Server", WEBSERV_ID); + _response.setHeader("Server", _virtualHost->getExternalServerId()); if (_response.getHeader("Content-Length").empty()) _response.setHeader("Content-Length", "0"); if (_response.getHeader("Content-type").empty()) diff --git a/src/http/VirtualHost.cpp b/src/http/VirtualHost.cpp index 6932eac..b63e430 100644 --- a/src/http/VirtualHost.cpp +++ b/src/http/VirtualHost.cpp @@ -1,15 +1,17 @@ #include "VirtualHost.hpp" #include "utils.hpp" +#include "webserv.hpp" std::vector VirtualHost::_virtualHosts; std::map VirtualHost::_mimeTypes; -VirtualHost::VirtualHost() {} +VirtualHost::VirtualHost() : _externalServerId(WEBSERV_NAME) {} VirtualHost::VirtualHost(const Context &context) { _context = context; + setExternalServerId(); std::vector > &listens = _context.getDirective("listen"); @@ -22,6 +24,7 @@ VirtualHost::VirtualHost(const VirtualHost &rhs) { *this = rhs; } VirtualHost &VirtualHost::operator=(const VirtualHost &rhs) { if (this == &rhs) return *this; _context = rhs._context; + _externalServerId = rhs._externalServerId; _resolvedListenDirective = rhs._resolvedListenDirective; return *this; } @@ -36,8 +39,6 @@ void VirtualHost::setMimeTypes(std::map &mimeTypes) { _mimeTypes = mimeTypes; } -void VirtualHost::setContext(const Context &context) { _context = context; } - std::vector &VirtualHost::getVirtualHosts() { return _virtualHosts; } @@ -57,6 +58,10 @@ std::set
const &VirtualHost::getResolvedAddress() const { Context &VirtualHost::getContext() { return _context; } +const std::string &VirtualHost::getExternalServerId() const { + return _externalServerId; +} + VirtualHost *VirtualHost::matchVirtualHost(Address &address, std::string host) { std::vector possibleHosts; @@ -110,3 +115,11 @@ Context *VirtualHost::matchLocation(const std::string &uri) { } return match; } + +void VirtualHost::setExternalServerId() { + if (_context.exists("server_tokens", true) && + _context.getDirective("server_tokens", true)[0][0] == "on") + _externalServerId = WEBSERV_ID; + else + _externalServerId = WEBSERV_NAME; +}