Chào các bạn,
Hôm nay, mình muốn chia sẻ với các bạn một ý tưởng thú vị trong lập trình Java, đó là tạo một Servlet Container đơn giản sử dụng ServerSocket - một interface trong gói network của Java. Giống như một số servlet container nổi tiếng như Tomcat hay Jetty, mình sẽ thử nghiệm cách thức mà chúng hoạt động, mặc dù sản phẩm của mình sẽ rất đơn giản và dễ dàng hơn nhiều. 😂
Mục Tiêu Của Bài Viết
Bài viết này sẽ hướng dẫn bạn từng bước để tạo ra một Servlet Container cơ bản, phục vụ cho việc xử lý HTTP requests. Mình sẽ cập nhật chi tiết dần dần trong các bài viết tới. Bạn có thể tìm thấy mã nguồn trong repository kèm theo bài viết.
Chuẩn Bị Nguyên Liệu
Để bắt đầu, các bạn cần định nghĩa một số lớp và interface cơ bản như sau:
1. SimpleServletRequest
Interface này tương tự như HttpServletRequest và bao gồm các phương thức giúp xử lý HTTP request:
String getMethod();
String getPath();
String getHeader(String name);
String getBody();
2. SimpleServletResponse
Interface này như HttpServletResponse với các phương thức liên quan đến việc xử lý HTTP response:
void setStatus(int statusCode);
void setHeader(String name, String value);
void writeBody(String body);
void sendResponse() throws Exception;
3. CabinServletContainer
Tên gọi Cabin
không có nhiều ý nghĩa sâu xa, chỉ đơn giản là tên mình thích. Servlet Container này sẽ giúp chúng ta đăng ký các handler và xử lý requests. Các phương thức chính bao gồm:
void registerServlet(String path, SimpleServlet servlet);
void start(int port);
void handleRequest(Socket clientSocket);
Bắt Đầu Xây Dựng Servlet Container
Chúng ta sẽ triển khai từng lớp một cách đơn giản để tạo ra Servlet Container.
1. Triển Khai SimpleServletRequestImpl
java
public class SimpleServletRequestImpl implements SimpleServletRequest {
// Implement the interface methods here
}
2. Triển Khai SimpleServletResponseImpl
java
public class SimpleServletResponseImpl implements SimpleServletResponse {
private OutputStream outputStream;
private int statusCode = 200;
private Map<String, String> headers = new HashMap<>();
private StringBuilder body = new StringBuilder();
public SimpleServletResponseImpl(OutputStream outputStream) {
this.outputStream = outputStream;
}
// Implement the interface methods
}
3. Xây Dựng CabinServletContainer
java
public class CabinServletContainer {
private Map<String, SimpleServlet> servlets = new HashMap<>();
public void registerServlet(String path, SimpleServlet servlet) {
servlets.put(path, servlet);
servlet.init();
}
public void start(int port) throws Exception {
// Code to start the server here
}
private void handleRequest(Socket clientSocket) {
// Code to handle request here
}
}
Chạy Server
Dưới đây là cách thức để chạy server và kiểm tra nó:
java
public static void main(String[] args) throws Exception {
CabinServletContainer container = new CabinServletContainer();
// Register a simple servlet
container.registerServlet("/hello", new SimpleServlet() {
// Implement the SimpleServlet methods
});
container.start(8080);
}
Kiểm Tra Server
Sau khi hoàn thành, bạn có thể sử dụng lệnh curl để kiểm tra server:
bash
curl http://localhost:8080/hello
curl http://localhost:8080/increment
Nhận Xét Cuối Bài
Bài viết này nhằm mục đích giúp bạn hiểu hơn về cách hoạt động của một web server cơ bản, cũng như cách xử lý các HTTP requests. Mặc dù version này còn nhiều hạn chế và chưa hỗ trợ đa luồng, session hay cookie, nhưng đây là một điểm bắt đầu tuyệt vời cho những ai muốn tìm hiểu về servlet container.
Cảm ơn các bạn đã theo dõi. Hãy đón đọc những bài viết tiếp theo, nơi mình sẽ cải tiến và hoàn thiện hơn nhé!
source: viblo