A feature complete HTTP/1.1 web server built entirely from scratch using Java's raw ServerSocket and Socket APIs completely framework free.
This repository serves as a step by step educational blueprint demonstrating low level networking, manual byte level protocol parsing, multi-threaded concurrency models, security controls, and strict compliance with modern RFC standards.
- Multi-Threaded Architecture: Concurrently isolates and processes incoming client sockets via independent worker threads to ensure non-blocking connection lifecycles.
- Byte-by-Byte Request Parsing: Implements a strict protocol parsing loop that manually decodes HTTP request lines and header configurations directly from the network stream.
- Conditional Caching (RFC 7232): Dynamically computes file
ETagchecksums (combining file size and last modified attributes) to deliver rapid304 Not Modifiedbrowser optimizations. - Partial Content & Range Requests (RFC 7233): Parses the
Range: bytes=start-endheader to stream designated byte subarrays, enabling media seeking and buffering (like.mp4video streaming) via HTTP206 Partial Content. - Basic Authentication Routing: Restricts sensitive target domains (paths starting with
/admin) by evaluating Base64 tokens and triggering a401 Unauthorizedcredentials challenge header. - Directory Traversal Defenses: Hardens file lookups against relative directory climbing manipulation (e.g.,
../../etc/passwd) by enforcing normalization checks against the web root folder boundary.
Client ──► [Port 8080] ──► ServerListenerThread
│
├──► (Accepts Socket) ──► Spawns HttpConnectionWorkerThread
│
├──► Parses HttpRequest via InputStream
├──► Validates Path & Routing Security
└──► Transmits Response via HttpResponse
The server boots by reading configuration parameters (port and webroot) from an external JSON file managed via a thread safe Singleton ConfigurationManager. The master supervisor loop (ServerListenerThread) binds onto the configured TCP port and delegates every incoming client connection directly to an independent HttpConnectionWorkerThread to keep the main listening loop completely non blocking.
Instead of loading the entire request string blindly into memory (which exposes the server to buffer overflow exploits), the custom HttpRequestParser reads raw bytes sequentially from the input stream. It tracks specific protocol delimiters like spaces (0x20) and CRLF (\r\n) to safely isolate and extract:
- The HTTP Method (validated against an internal
HttpMethodEnum) - The Request Target URI (enforced with a strict 8000-character safety limit)
- A structured map of case-insensitive HTTP Headers
To prevent Directory Traversal vulnerabilities, incoming targets are resolved using absolute path calculations (.toAbsolutePath().normalize()). The worker verifies that the requested file resides strictly within the bounds of the configured web root directory. Furthermore, access to administrative targets (e.g., /admin) is automatically intercepted, requiring a valid Base64-encoded credentials header (Basic YWRtaW46cGFzc3dvcmQ=). Missing or incorrect tokens immediately issue a 401 Unauthorized challenge response.
The server goes beyond simple text based responses to handle binary payloads and browser optimization protocols:
- MIME-Type Resolution: Automatically maps file extensions (
.html,.css,.js,.png,.jpg,.mp4) to their appropriateContent-Typeheaders. - ETag Cache Validation: Computes an asset signature using the file size and last modified date. If the client’s incoming
If-None-Matchheader matches this token, the server bypasses the disk read and drops a lightweight304 Not Modifiedstatus code. - Partial Content Extraction: Inspects incoming client requests for
Range: bytes=s-estrings. If present, it extracts the requested byte sub slice from memory and returns an HTTP206 Partial Contentresponse, allowing browsers to seamlessly stream large video files.
- Java Development Kit (JDK) 23 or higher
- Apache Maven
- Clone the repository:
git clone [https://github.com/your-username/build-a-https-server-from-scratch.git](https://github.com/your-username/build-a-https-server-from-scratch.git) cd build-a-https-server-from-scratch/http_server - Verify Configuration:
Check the server parameters located at
src/main/resources/http.json:{ "port" : 8080, "webroot" : "src/main/resources/html" } - Build the Project:
mvn clean package
- Run the Server:
java -cp target/http_server-1.0-SNAPSHOT.jar com.minor.httpserver.Http_Server
Open your browser and navigate to http://localhost:8080 to see your running web server!