{"id":28091394,"url":"https://github.com/mitadic/webserv","last_synced_at":"2025-05-13T13:06:49.955Z","repository":{"id":289476985,"uuid":"918999280","full_name":"mitadic/webserv","owner":"mitadic","description":"NGINX prototype built using historical stack [ C++98, poll() ]","archived":false,"fork":false,"pushed_at":"2025-05-04T12:29:07.000Z","size":30464,"stargazers_count":1,"open_issues_count":0,"forks_count":1,"subscribers_count":1,"default_branch":"dev","last_synced_at":"2025-05-04T13:29:11.555Z","etag":null,"topics":["cgi","cpp98","http-server","http1-1","linux","macos"],"latest_commit_sha":null,"homepage":"","language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"cc0-1.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mitadic.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2025-01-19T13:01:42.000Z","updated_at":"2025-04-26T14:59:04.000Z","dependencies_parsed_at":null,"dependency_job_id":"d158d50c-828b-4a33-a14b-ae7609437d25","html_url":"https://github.com/mitadic/webserv","commit_stats":null,"previous_names":["mitadic/webserv"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mitadic%2Fwebserv","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mitadic%2Fwebserv/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mitadic%2Fwebserv/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mitadic%2Fwebserv/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mitadic","download_url":"https://codeload.github.com/mitadic/webserv/tar.gz/refs/heads/dev","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":253948417,"owners_count":21988953,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cgi","cpp98","http-server","http1-1","linux","macos"],"created_at":"2025-05-13T13:01:27.199Z","updated_at":"2025-05-13T13:06:49.922Z","avatar_url":"https://github.com/mitadic.png","language":"C++","funding_links":[],"categories":[],"sub_categories":[],"readme":"\n# Webserv\n\nProject by [@mitadic](https://github.com/mitadic), [@chilituna](https://github.com/chilituna) and [@pebencze](https://github.com/pebencze). 🚀🌐\n\n## Table of Contents\n- [About](#about)\n- [Usage](#usage)\n- [Features](#features)\n- [Configuration File](#configuration-file)\n- [Terminology](#terminology)\n- [Resources](#resources)\n\n## About\n\nWebserv is a rudimentary prototype of an HTTP 1.1 server built using C++ 98 and [poll()](https://man7.org/linux/man-pages/man2/poll.2.html), with no external libraries utilized. It can serve both static files from a root directory and dynamic content using CGI (Common Gateway Interface), as it is compliant with RFC 2616 and RFC 3875.\n\n\u003cp float=\"left\"\u003e\n\t\u003cimg src=\"./readme/index.png\" alt=\"Website\" width=\"220\"\u003e\n\t\u003cimg src=\"./readme/coffee.png\" alt=\"Website\" width=\"220\"\u003e\n\t\u003cimg src=\"./readme/about.png\" alt=\"Website\" width=\"220\"\u003e\n\t\u003cimg src=\"./readme/setup.png\" alt=\"Website\" width=\"440\"\u003e\n\t\u003cimg src=\"./readme/requests.png\" alt=\"Website\" width=\"440\"\u003e\n\u003c/p\u003e\n\n## Usage\n\n### 1. Build the Project\nTo compile the project after cloning and entering the cloned directory, run:\n```bash\nmake\n```\n\n### 2. Run the Server\n#### Using the Default Config File\n```bash\n./webserv\n```\n\n#### Using a Custom Config File\n```bash\n./webserv [config_file]\n```\n\n#### Setting a Custom Debug Level\nYou can specify debug levels: `SETUP`, `DEBUG`, `INFO`, `WARNING`, or `ERROR`. The default one is `INFO`.\n```bash\n./webserv [debug_level]\n```\n\n### 3. Make Requests\n#### Using a Web Browser\nOpen a browser (Chrome or Firefox) and navigate to:\n```\nhttp://127.0.0.1:8080\nhttp://127.0.0.1:8081\n```\n\n#### Using Telnet\n```bash\ntelnet localhost 8080\n```\n\n#### Using cURL\n```bash\n# Example GET request\ncurl -v http://localhost:8080/index.html\n\n# Example DELETE request\ncurl -X DELETE http://localhost:8080/uploads/hi.txt\n\n# Example POST request (uploading a file)\ncurl -v -X POST http://localhost:8080/uploads -F \"file=@test.txt\"\n```\n\n### 4. Run a collection of End-To-End Test\n```bash\nmake test\n```\n\n## Features\n\n* ✅ Implemented and tested.\n* 🚧 In Progress.\n* 🟥 Not Implemented.\n\n\nFeature | Status\n:--- | :---\nDirect resource management with `GET` `TEST` `DELETE` | ✅\nNon-blocking I/O | ✅\nRedirections | ✅\nCGI for .py and .php with `GET` `POST` | ✅\nCookies | ✅\nHTTP/1.0 and 1.1 per RFC [2616](https://datatracker.ietf.org/doc/html/rfc2616) | ✅\nHTTPS | 🟥\nMultithreaded workers | 🟥\nMac- and Linux-compatibility | ✅\nPipelining within single TCP segment | 🚧\n\n## Configuration File\n\nThe configuration file is inspired by the default NGINX configuration. It uses a simple structure with **server blocks** that listen on specific IP addresses and ports. Each server block can include **location directives** to define rules or configurations for specific paths.\n\n### Directives\n\nThe available `.conf` directives and their purposes:\nDirective | Purpose\n:--- | :---\n**`host [ip address]`** | Specifies the IP address the server will bind to.\n**`listen [port number]`** | Defines the port number the server will listen on.\n**`client_max_body_size [number of bytes]`** | Sets the maximum allowed size for the client request body.\n**`error_page [status code] [relative path]`** | Sets a custom error page for a specific HTTP status code.\n**`root [root of the location]`** | Specifies the root directory for serving files.\n**`index [default page to be served]`** | Defines the default file to serve when accessing a directory.\n**`allowed_methods [GET , POST , DELETE]`** | Allows HTTP methods for a location.\n**`autoindex [on \\|\\| off]`** | Enables or disables directory listing when no index file is found.\n**`upload [path to upload folder]`** | Specifies the directory where uploaded files will be stored.\n**`return [status code] [new location]`** | Redirects requests to a new location with a specific status code.\n**`cgi_extension [.py , .sh , .php]`** | Defines the file extensions that will be processed using CGI.\n\n### Example Configuration\n\nThis example demonstrates a basic configuration with a root directory, an upload location, and a custom error page.\n\n```conf\nserver {\n\thost 127.0.0.1;\n\tlisten 8080;\n\n\tclient_max_body_size 10485760;\n\n\terror_page 404 /404.html;\n\n\tlocation / {\n\t\troot /var/www/html;\n\t\tindex index.html;\n\t\tallowed_methods GET;\n\t}\n}\n```\n\n## The Status Codes utilized\nMeaning | Code | Scenario Example\n:--- | :--- | :---\nOK | 200 | Generic \"all good\". E.g. page delivered\nCreated | 201 | Confirming upload or form submission\nAccepted | 202 | Confirming arrival (noncommittal)\nNo Content | 204 | DELETE success\nMoved Permanently | 301 | Try to not ask for this URI in the future\nFound | 302 | You can expect to find stuff at this URI later again\nTemporary Redirect | 307 | Same semantics as `302`, but method must persist\nPermanent Redirect | 308 | Same semantics as `301`, but method must persist\nBad Request | 400 | Generic \"it's not me it's you\"\nForbidden | 403 | Directory deletion not allowed, missing index.html, etc\nNot found | 404 | No resource at specified URI\nMethod not allowed | 405 | Trying to `DELETE` at specific location\nNot Acceptable | 406 | Client does not accept file type\nRequest Timeout | 408 | Connection established but no request ever came in\nLength Required | 411 | A `POST` request needs either `Content-Length` or `Transfer-Encoding` information\nContent Too Large | 413 | Request body is larger than limits defined by server\nURI Too Long | 414 | Longer than default (Webserv sets 4096)\nUnsupported Media Type | 415 | Format not supported by the server\nI'm a teapot | 418 | You asked for coffee in the URI and Webserv refused\nInternal Server Error | 500 | Generic \"it's not you it's me\"; undisclosed backend failure\nNot Implemented | 501 | e.g. method DELETE in a CGI request, not a feature of Webserv\nService Unavailable | 503 | Conventionally sent with a `Retry-After`\nGateway Timeout | 504 | CGI timeout\nHTTP Version Not Supported | 505 | e.g. HTTP/2.0\n\n\n## Terminology\n### NGINX\n\nNGINX (used by Netflix, Instagram etc.) is a high-performance web server designed for handling a large number of connections. Among many other protocols it supports HTTP/1.1. Nginx has a lot of useful features that our program does not have, e.g. it is a reverse proxy, it supports SSL/TLS and streaming.\n\n\n### HTTP\n\nThe Hypertext Transfer Protocol (HTTP) is an application-level\nprotocol for distributed, collaborative, hypermedia information\nsystems.\n\nThe overall protocol as defined in RFC [2616](https://datatracker.ietf.org/doc/html/rfc2616):\n\n\u003e \"The HTTP protocol is a request/response protocol. A client sends a\nrequest to the server in the form of a request method, URI, and\nprotocol version, followed by a MIME-like message containing request\nmodifiers, client information, and possible body content over a\nconnection with a server. The server responds with a status line,\nincluding the message's protocol version and a success or error code,\nfollowed by a MIME-like message containing server information, entity\nmetainformation, and possible entity-body content.\"\n\u003e\n### Web Server\nThe term can refer to hardware or software or both working together. A web server software controls how users can access hosted files. An HTTP server can be accessed through the domain names of the websites it stores. On the hardware side, the web server stores the software and the website’s component files (HTML docs, images, CSS sheets). It connects to the internet and supports data exchange with *clients*.\n\n### Non-Blocking\n##### Blocking (Kerrisk 2010, page 1325):\n\u003e \"Most of the [core linux programs] employ an I/O model under which a process performs I/O on just one file descriptor at a time, and each I/O system call blocks [the thread] until the data is transferred.\"\n\n##### Multiplexing (Kerrisk 2010, page 1327):\n\u003e \"In effect, I/O multiplexing, signal-driven I/O, and epoll are all methods of achieving the same result—monitoring one or, commonly, several file descriptors simultaneously to see if they are ready to perform I/O (to be precise, to see whether an I/O system call could be performed without blocking). The transition of a file descriptor into a ready state is triggered by some type of I/O event, such as the arrival of input, the completion of a socket connection, or the availability of space in a previously full socket send buffer after TCP transmits queued data to the socket peer.\"\n\n\u003e \"Monitoring multiple file descriptors is useful in applications such as network servers that must simultaneously monitor multiple client sockets, or applications that must simultaneously monitor input from a terminal and a pipe or socket. Note that none of these techniques performs I/O. They merely tell us that a\nfile descriptor is ready. Some other system call must then be used to actually perform the I/O.\"\n\n## Resources\n* Requests For Comments (documentation of the HTTP/1.1 protocol, administered by the Internet Engineering Taskforce; the golden standards of HTTP):\n\t* [RFC2616](https://datatracker.ietf.org/doc/html/rfc2616): 1999 RFC for HTTP/1.1\n\t* [RFC9112](https://datatracker.ietf.org/doc/html/rfc9112): latest version\n\t* [RFC9110](https://datatracker.ietf.org/doc/html/rfc9110): latest version\n\t* [RFC3875](https://datatracker.ietf.org/doc/html/rfc3875): RFC for the CGI\n* [Linux manual section 2 pages](https://man7.org/linux/man-pages/dir_section_2.html)\n* The Linux Programming Interface by Michael Kerrisk (2010)\n* Medium articles:\n\t* [Setting up a server](https://medium.com/@ahmadesekak/setting-up-a-server-using-c-sockets-124e404593c9)\n\t* [Building a non-blocking web server](https://m4nnb3ll.medium.webserv-building-a-non-blocking-web-server-in-c-98-a-42-project-04c7365e4ec7)\n* [Beej's Guide to Network Programming](https://beej.us/guide/bgnet/html/split/client-server-background.html#a-simple-stream-server)\n* [Beej's Guide to IPC](https://beej.us/guide/bgipc/html/split-wide/)\n* [Nginx directory structure](https://wiki.debian.org/Nginx/DirectoryStructure)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmitadic%2Fwebserv","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmitadic%2Fwebserv","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmitadic%2Fwebserv/lists"}