Buộc vẽ lại thành phần React mà không cần setState
By hunglv, at: 09:07 Ngày 22 tháng 9 năm 2025
Thời gian đọc ước tính: __READING_TIME__ phút


Vấn đề:
Trong React, đôi khi, bạn cần ép một thành phần tái-render ngay cả khi không có thay đổi có ý nghĩa nào trong trạng thái của nó. Ví dụ: bạn có thể đang lắng nghe một sự kiện bên ngoài (ví dụ: WebSocket, trình phát sự kiện hoặc cửa hàng tùy chỉnh) không ảnh hưởng đến trạng thái cục bộ của thành phần nhưng vẫn cần cập nhật hình ảnh.
Kịch bản thông thường:
useEffect(() => {
someObservable.on('data', () => {
// Nhưng không có trạng thái nào được đặt ở đây
// Thành phần sẽ không tái-render!
});
}, []);
Giải pháp: Sử dụng trạng thái giả hoặc một Reducer
Đối với Thành phần Hàm:
Sử dụng một useState hoặc useReducer giả để kích hoạt tái-render thủ công.
const [, forceUpdate] = useReducer(x => x + 1, 0);
useEffect(() => {
const handleUpdate = () => forceUpdate();
someObservable.on('data', handleUpdate);
return () => someObservable.off('data', handleUpdate);
}, []);
Đối với Thành phần Lớp:
Sử dụng phương thức this.forceUpdate().
componentDidMount() {
this.listener = () => this.forceUpdate();
someObservable.on('data', this.listener);
}
componentWillUnmount() {
someObservable.off('data', this.listener);
}
Ưu điểm và Nhược điểm
Ưu điểm:
-
Cho phép bạn tích hợp với các nguồn trạng thái không phải của React (như các cửa hàng bên ngoài hoặc trình phát sự kiện).
-
Đơn giản và hiệu quả đối với các kích hoạt một lần mà không cần thêm các biến trạng thái không cần thiết.
-
Tránh làm rối loạn thành phần với trạng thái vô nghĩa chỉ để kích hoạt tái-render.
Nhược điểm:
-
Không khai báo rõ ràng lắm, bạn đang bỏ qua luồng dữ liệu/trạng thái thông thường của React.
-
Sử dụng quá mức có thể cho thấy các vấn đề về kiến trúc; hãy xem xét việc tái cấu trúc hoặc sử dụng một giải pháp quản lý trạng thái phù hợp.
-
Sử dụng forceUpdate() trong các thành phần lớp được coi là giải pháp cuối cùng và có thể dẫn đến mã khó bảo trì hơn.
Mẹo dành cho Nhà phát triển:
Nếu bạn thường xuyên ép tái-render, hãy xem xét xem cấu trúc thành phần hoặc phương pháp quản lý trạng thái của bạn có cần cập nhật không. React Context, Zustand, Redux, hoặc thậm chí các hook tùy chỉnh có thể cung cấp một giải pháp sạch hơn.