504 Gateway Timeout nghĩa là máy chủ phía trước — thường là Nginx hoặc một load balancer — đã chuyển tiếp yêu cầu của bạn tới backend, rồi ngồi chờ, và cuối cùng bỏ cuộc. Backend không từ chối, không sập, nó chỉ đơn giản chưa trả lời kịp.
Phân biệt được điều này với 502 giúp tiết kiệm rất nhiều thời gian. 502 nghĩa là backend trả về thứ gì đó vô nghĩa hoặc đã chết; 504 nghĩa là nó vẫn đang chạy, vẫn đang làm việc, chỉ là chậm hơn giới hạn kiên nhẫn được cấu hình sẵn. Gần như mọi lần sửa 504 đều quy về một trong hai việc: làm cho công việc nhanh lên, hoặc nâng giới hạn chờ — và thứ tự đó không nên đảo ngược.
504 khác 502, 503 và 408 ra sao
Bốn mã này đều xuất hiện khi có gì đó sai giữa proxy và ứng dụng, nhưng mỗi mã chỉ về một chỗ khác nhau.
| Mã | Chuyện gì đã xảy ra | Nhìn vào đâu trước |
|---|---|---|
| 504 Gateway Timeout | Backend còn sống nhưng trả lời quá chậm | Truy vấn chậm, API bên ngoài, tiến trình chạy dài |
| 502 Bad Gateway | Backend chết hoặc trả về phản hồi hỏng | Log crash của PHP-FPM, Node, Gunicorn |
| 503 Service Unavailable | Máy chủ chủ động từ chối nhận thêm việc | Hàng đợi đầy, bảo trì, giới hạn tốc độ |
| 408 Request Timeout | Máy khách gửi yêu cầu quá chậm | Mạng phía người dùng, upload lớn |
Con số timeout nào đang thực sự hết hạn
Đây là phần khiến 504 khó chịu hơn cần thiết: một yêu cầu đi qua nhiều lớp, mỗi lớp có đồng hồ đếm ngược riêng, và lớp nào hết trước sẽ quyết định thông báo bạn nhìn thấy. Nâng nhầm con số thì chẳng thay đổi được gì.
| Lớp | Tham số thường gặp | Mặc định điển hình |
|---|---|---|
| Nginx → backend | proxy_read_timeout | 60 giây |
| Nginx → PHP-FPM | fastcgi_read_timeout | 60 giây |
| PHP | max_execution_time | 30 giây |
| PHP-FPM | request_terminate_timeout | thường tắt |
| Cloudflare (gói miễn phí) | timeout cố định | 100 giây — không đổi được |
Nguyên nhân thường gặp, phổ biến nhất trước
- Truy vấn cơ sở dữ liệu chậm. Nguyên nhân số một, gần như luôn là một truy vấn thiếu index quét toàn bộ bảng khi dữ liệu đã lớn lên.
- Gọi API bên ngoài không đặt timeout. Ứng dụng của bạn chờ một dịch vụ bên thứ ba đang chậm, và vì không giới hạn thời gian chờ nên nó chờ mãi.
- Tác vụ nặng chạy ngay trong yêu cầu HTTP. Xuất báo cáo, gửi hàng loạt email, xử lý ảnh — những việc này thuộc về hàng đợi nền chứ không phải chu kỳ yêu cầu.
- Hết worker. Mọi tiến trình PHP-FPM hoặc Node đều đang bận với các yêu cầu chậm, nên yêu cầu mới xếp hàng cho tới khi hết giờ mà chưa được xử lý.
- Cron chạy đè lên nhau. wp-cron trên site nhiều lượt truy cập kích hoạt theo mỗi lượt xem, chồng chất lên nhau và ăn hết worker.
- Máy chủ hết RAM và bắt đầu swap. Mọi thứ vẫn hoạt động, chỉ là chậm gấp hàng chục lần, và timeout xuất hiện trên toàn bộ website.
- Plugin hoặc thư viện thao tác mạng khi tải trang. Kiểm tra bản cập nhật, xác thực giấy phép, tải font từ xa — mỗi thứ thêm vài giây vào thời gian phản hồi.
Kiểm tra theo thứ tự này
- Xác định lỗi xảy ra ở mọi trang hay chỉ vài trang. Toàn site chậm thường là tài nguyên máy chủ; một trang cụ thể chậm gần như luôn là một truy vấn hoặc một lệnh gọi bên ngoài trên đúng trang đó.
- Đo thời gian phản hồi thật bằng "curl -o /dev/null -s -w '%{time_total}\n' https://trangcuaban.com/". Con số này cho biết bạn đang ở sát ngưỡng hay vượt xa nó.
- Bật slow query log của MySQL với ngưỡng 1 giây rồi để chạy vài phút. Đây là bước cho kết quả nhanh nhất trong toàn bộ danh sách.
- Xem error log của Nginx. Dòng "upstream timed out" ghi rõ backend nào và endpoint nào đã hết giờ.
- Kiểm tra RAM và swap bằng "free -m". Nếu swap đang được dùng nhiều, hãy xử lý bộ nhớ trước — mọi thứ khác chỉ là chữa triệu chứng.
- Đếm số worker đang bận so với tổng số. PHP-FPM có trang status; nếu luôn chạm trần pm.max_children, hàng đợi mới là vấn đề chứ không phải bản thân timeout.
- Tạm tắt các thành phần gọi mạng bên ngoài. Nếu 504 biến mất, bạn đã tìm được thủ phạm và có thể đặt timeout ngắn cho lệnh gọi đó.
- Chỉ nâng timeout sau khi đã biết chính xác cái gì chậm, và nâng như một biện pháp tạm thời có chủ đích, không phải như cách sửa.
Cách sửa đúng gốc
Khi đã biết chỗ nào chậm, cách xử lý gần như luôn rơi vào một trong ba nhóm dưới đây.
Thêm index cho truy vấn chậm. Một cột được lọc thường xuyên mà không có index sẽ khiến cơ sở dữ liệu đọc toàn bộ bảng ở mỗi yêu cầu. Chạy EXPLAIN trên truy vấn chậm nhất trong log; nếu thấy quét toàn bảng, bạn đã có việc cần làm và thường mất chưa tới một phút.
Đưa việc chạy lâu ra khỏi chu kỳ yêu cầu. Xuất file, gửi email, tạo thumbnail và đồng bộ dữ liệu nên chạy trong hàng đợi nền, còn yêu cầu HTTP chỉ trả về ngay lập tức rằng công việc đã được nhận. Đây là thay đổi tốn công nhất nhưng cũng là thay đổi loại bỏ vĩnh viễn cả một nhóm lỗi 504.
Đặt timeout cho mọi lệnh gọi ra ngoài. Bất kỳ yêu cầu nào tới dịch vụ bên thứ ba đều phải có giới hạn thời gian vài giây kèm cách xử lý khi thất bại. Không có nó, một API chậm ở đầu kia thế giới sẽ trực tiếp trở thành trang lỗi của bạn.
Nếu tất cả đều đã hợp lý mà máy chủ vẫn không đủ sức, lúc đó vấn đề mới thực sự là tài nguyên. CPU luôn cao, RAM luôn cạn và swap hoạt động liên tục là dấu hiệu thật cho việc nâng cấp — khác hẳn với việc nâng cấp chỉ vì thấy 504.
Cần tài nguyên đủ để không phải chạy đua với timeout?
Cloud VPS NVMe với quyền root đầy đủ — tự chỉnh timeout, slow query log và số worker theo ý mình. Từ ฿150/tháng.
Câu hỏi thường gặp
Tôi đã nâng timeout mà vẫn bị 504. Vì sao?
Vì bạn nâng nhầm lớp. Một yêu cầu đi qua Nginx, rồi PHP-FPM hoặc application server, rồi tới cơ sở dữ liệu, và mỗi lớp có timeout riêng — lớp nào ngắn nhất sẽ thắng. Nếu website chạy sau Cloudflare gói miễn phí, còn có trần cứng 100 giây mà không cấu hình nào trên máy chủ vượt được.
504 có ảnh hưởng SEO không?
Có, nếu kéo dài. Googlebot gặp 504 sẽ thử lại sau, và vài lần lẻ tẻ hầu như không gây hại gì. Nhưng timeout liên tục nhiều ngày sẽ làm giảm tốc độ thu thập và cuối cùng khiến trang rơi khỏi chỉ mục. Báo cáo Crawl stats trong Search Console cho biết Googlebot thực sự gặp bao nhiêu lỗi.
Vì sao 504 chỉ xảy ra vào giờ cao điểm?
Vì bạn đang cạn worker chứ không phải cạn thời gian. Khi mọi tiến trình đều bận, yêu cầu mới phải xếp hàng và đồng hồ timeout bắt đầu chạy trước cả khi có ai xử lý chúng. Hãy tìm truy vấn chậm giữ worker quá lâu, thay vì tăng số worker lên rồi lại cạn RAM.
Trang admin WordPress bị 504 nhưng phần công khai vẫn ổn. Vì sao?
Vì trang admin không được cache và chạy nhiều truy vấn hơn hẳn. Nguyên nhân phổ biến nhất là bảng wp_options phình to vì transient hết hạn, hoặc plugin kiểm tra cập nhật khi tải trang. Dọn transient cũ và tắt plugin lần lượt để tìm thủ phạm.
GUIDES
Bài viết liên quan
Đọc tiếp các chủ đề tương tự
502 Bad Gateway — Ý nghĩa và cách khắc phục
502 nghĩa là một máy chủ đã hỏi máy chủ khác để lấy trang và nhận về thứ không dùng được. Bài này giải thích hai máy nào đang liên quan, khác biệt với 500 và 504, cùng thứ tự kiểm tra để bạn tìm đúng nguyên nhân trước tiên.
Đọc tiếp503 Service Unavailable — Nguyên nhân và cách khắc phục
503 khác mọi lỗi 5xx còn lại ở một điểm: rất nhiều trường hợp nó là câu trả lời có chủ đích. Máy chủ vẫn hoạt động, vẫn hiểu yêu cầu, và chủ động nói rằng bây giờ nó không nhận việc.
Đọc tiếp500 Internal Server Error — Nguyên nhân và cách sửa
500 là lỗi ít thông tin nhất trên web: nó nghĩa là "có gì đó hỏng và tôi sẽ không nói là gì". Tin tốt là máy chủ gần như luôn ghi lý do thật vào một file log. Bài này chỉ chỗ file đó và thứ tự kiểm tra nhanh nhất để tìm ra thủ phạm.
Đọc tiếp