Chúng ta sẽ tìm hiểu về quá trình của một request được gửi đến Laravel framework. Nếu như bạn hiểu cách thức hoạt động của một công cụ nào đó thì bạn có thể sử dụng nó một cách tự tin và hiệu quả nhất, Laravel framework cũng vậy. Chính vì thế tập này khá quan trọng cho những bạn “chân ướt chân ráo” mới tìm hiểu về framework này.
1. Mô hình vòng đời request Laravel
Hãy quan sát mô hình vòng đời của một request khi được gửi đến trong Laravel framework:
2. Khởi động (Bootstrap)
Đầu tiên từ phía client sẽ gửi một request đến file public/index.php
, nó là đích đến của tất cả các request từ client. Dù code không nhiều nhưng nó là khởi nguyên cho framework.
Mở file public/index.php
lên và xem code của nó, các bạn sẽ thấy nó làm 3 nhiệm vụ chính để bootstrap framework.
- Đăng ký cơ chế autoload (Register the auto loader)
- Chuẩn bị để khởi động ứng dụng (Prepare to bootstrap the application)
- Chạy ứng dụng (Run the application)
3. HTTP/Console Kernel
Tiếp theo, request sẽ được gửi đến HTTP Kernel hoặc Console Kernel, tùy thuộc vào request được gửi từ đâu. Hiện tại chúng ta chỉ quan tâm đến HTTP Kernel nằm ở file app/Http/Kernel.php
.
HTTP Kernel kế thừa class Illuminate\Foundation\Http\Kernel
, class này sẽ thực việc các công việc trước khi request được thực thi như cấu hình xử lý lỗi, cấu hình logger, xác định môi trường ứng dụng và một số công việc khác.
HTTP Kernel cũng thực hiện một số middleware mặc định của Laravel buộc các request phải vượt qua trước khi được ứng dụng xử lý như kiểm tra ứng dụng có đang ở chế độ bảo trì không, xác thực CSRF (sẽ tìm hiểu ở các tập sau), thao tác với HTTP session…
HTTP Kernel như một chiếc “hộp đen” của ứng dụng, hoạt động theo cơ chế đơn giản: nhận request và trả về response.
Bắt đầu từ những chốt chặn sau đều nằm trong chiếc “hộp đen” HTTP Kernel này.
4. Service providers
Một trong những công việc quan trọng nhất của HTTP Kernel đó chính là load các service provider. Tất cả các service provider được cấu hình trong file config/app.php
. Quá trình load các service provider sẽ trải qua hai quá trình:
- Đăng ký service provider (Register service provider)
- Khởi động service provider (Bootstrap service provider)
Các service provider khởi động nhiều thành phần khác nhau của framework như database, validation, router… Chính vì thế mà nó đóng vai trò thiết yếu trong quá trình chạy ứng dụng Laravel.
5. Router
Sau khi hoàn tất load service provider, các request sẽ được gửi đến router. Chốt chặn này rất dễ hiểu, việc này giống như bạn tìm nhà cho một đứa trẻ đi lạc vậy. Công việc của router sẽ kiểm tra tất cả các route đã được khai báo trong các file ở thư mục routes
so với request được gửi đến. Nếu khớp hoàn toàn với một route nào đó thì sẽ có hai hướng xử lý. Hãy quan sát mô hình ở phía trên, tại chốt chặn route có hai hướng rẽ:
- Route -> Middleware -> Controller/Action
- Route -> Controller/Action
Tại sao lại có hai hướng xử lý như vậy? Khi khai báo route, Laravel cho phép ta có thể ràng buộc request đi qua bằng các middleware tự tạo. Chính vì vậy mà tùy vào mỗi route có ràng buộc middleware hay không nên mình chia hai hướng xử lý như vậy để bao quát.
6. Middleware
Như đã nói ở trên, để ứng dụng có thể xử lý được request mà route đã đăng ký middleware thì không còn cách nào khác phải vượt qua nó. Tại đây, middleware sẽ xử lý logic theo những ràng buộc mà coder đặt ra để quyết định xem request đó có được đi tiếp hay là không.
7. Phương thức xử lý (Handle method)
Có hai phương thức xử lý request đó chính là controller hoặc action (Closure object). Nhìn chung thì hai phương thức này đều hoạt động như nhau nhưng cách thể hiện và hiệu năng lại khác nhau.
Controller là thành phần của mô hình MVC nên về tối ưu và hiệu năng hơn hẳn action, rất dễ dàng quản lý và mở rộng.
Về action thường dành cho những phương thức xử lý ngắn gọn như trả về một view, hay return một object, array… thường dành cho test hoặc trong quá trình học.
8. Phương thức trả về (Return method)
Quan sát trên mô hình, ta thấy có hai mũi tên màu đỏ trả về phía client, đó chính là response. Nhưng sao lại có hai hướng như vậy, đó là do chúng ta có hai cách thức để trả về response:
- Trả về response thông qua
View
- Trả về response không thông qua
View
Hai hình thức này cũng không có điểm gì khác biệt mấy, mình chia nhánh như vậy để đồng bộ mô hình. View
chứa các template đã được khai báo sẵn, khi trả về chỉ kèm theo các tham số tùy biến. Trả về response thông qua View
chỉ thường áp dụng khi load giao diện, phương thức hay dùng vẫn là phương thức còn lại.