Cookies và Sessions
Trong Node.js (đặc biệt là với Express.js), Cookies và Sessions là hai cơ chế cốt lõi được sử dụng để lưu trữ trạng thái của người dùng, vì giao thức HTTP mặc định là Stateless (không lưu lại trạng thái giữa các lần gửi yêu cầu). Mối quan hệ cốt lõi giữa hai khái niệm […]
Trong Node.js (đặc biệt là với Express.js), Cookies và Sessions là hai cơ chế cốt lõi được sử dụng để lưu trữ trạng thái của người dùng, vì giao thức HTTP mặc định là Stateless (không lưu lại trạng thái giữa các lần gửi yêu cầu).
Mối quan hệ cốt lõi giữa hai khái niệm này: Session giống như chiếc két sắt bảo mật nằm trên Server, còn Cookie là chiếc chìa khóa nhỏ giao cho Client nắm giữ để mở chiếc két đó.
Cookies là gì?
Cookie là các tệp văn bản nhỏ được Server tạo ra nhưng lại được lưu trữ trực tiếp tại Trình duyệt (Client). Mỗi khi trình duyệt gửi request tiếp theo lên server, nó sẽ tự động đính kèm cookie này theo.
Cách cài đặt và sử dụng trong Express
Để làm việc với Cookie, bạn cần cài đặt thư viện bên thứ ba:
npm install cookie-parser.
const express = require('express');
const cookieParser = require('cookie-parser');
const app = express();
// Sử dụng middleware cookie-parser
app.use(cookieParser('chuoi_bi_mat_de_ky_cookie'));
// 1. Tạo (Set) Cookie gửi về cho Client
app.get('/set-cookie', (req, res) => {
res.cookie('user_theme', 'dark', {
maxAge: 900000, // Thời gian sống: 900,000 miligiây (15 phút)
httpOnly: true, // Bảo mật: Ngăn JavaScript phía Client tiếp cận (chống hack XSS)
secure: true, // Chỉ gửi cookie qua giao thức HTTPS bảo mật
signed: true // Ký tên cookie để phát hiện nếu Client cố tình sửa đổi dữ liệu
});
res.send('Đã lưu cấu hình giao diện tối vào Cookie!');
});
// 2. Đọc (Get) Cookie từ Client gửi lên
app.get('/get-cookie', (req, res) => {
// Nếu dùng signed: true thì đọc qua req.signedCookies, ngược lại dùng req.cookies
const theme = req.signedCookies.user_theme;
res.send(`Giao diện người dùng hiện tại: ${theme}`);
});
// 3. Xóa (Delete) Cookie
app.get('/clear-cookie', (req, res) => {
res.clearCookie('user_theme');
res.send('Đã xóa Cookie thành công!');
});
app.listen(3000);
Sessions là gì?
Session là cơ chế lưu trữ dữ liệu hoàn toàn trên Server. Trình duyệt client không hề biết bên trong session có dữ liệu gì. Nó chỉ giữ duy nhất một chuỗi mã hóa gọi là Session ID thông qua một Cookie.
Luồng hoạt động của Session:
- Client gửi yêu cầu đăng nhập.
- Server xác thực đúng, tạo ra một Session chứa thông tin user (ví dụ: tên, quyền hạn).
- Server cấp một mã định danh duy nhất Session ID (ví dụ: s%3Ajsdf923…) rồi nhét mã này vào Cookie gửi về Client.
- Lần sau Client gửi request, Server đọc Session ID từ Cookie rồi đối chiếu với kho lưu trữ trên Server để lấy ra thông tin User tương ứng.
Cách cài đặt và sử dụng trong Express
Bạn cần cài đặt thư viện:
npm install express-session.
const express = require('express');
const session = require('express-session');
const app = express();
// Cấu hình Middleware Session
app.use(session({
secret: 'khoa_bi_mat_sieu_cap', // Chuỗi dùng để mã hóa Session ID
resave: false, // Không lưu lại session nếu không có thay đổi
saveUninitialized: false, // Không tạo session trống cho user chưa đăng nhập
cookie: {
secure: false, // Để false nếu chạy localhost (HTTP), để true nếu chạy HTTPS
maxAge: 60000 * 30 // Session hết hạn sau 30 phút
}
}));
// 1. Đăng nhập và tạo Session
app.post('/login', (express.json()), (req, res) => {
const { username, password } = req.body;
// Giả định kiểm tra database thành công
if (username === 'admin' && password === '123') {
// Lưu thông tin vào session
req.session.isLoggedIn = true;
req.session.username = username;
return res.send('Đăng nhập thành công và đã tạo Session!');
}
res.status(401).send('Sai tài khoản!');
});
// 2. Kiểm tra Session ở route bảo mật
app.get('/profile', (req, res) => {
if (req.session.isLoggedIn) {
res.send(`Chào mừng quay trở lại, ${req.session.username}`);
} else {
res.status(401).send('Bạn chưa đăng nhập!');
}
});
// 3. Đăng xuất - Hủy Session
app.get('/logout', (req, res) => {
req.session.destroy((err) => {
if (err) return res.send('Không thể đăng xuất');
res.send('Đã hủy session và đăng xuất thành công!');
});
});
app.listen(3000);
Bảng so sánh nhanh để ghi nhớ
| Tiêu chí | Cookies | Sessions |
| Nơi lưu trữ | Trình duyệt Client (Máy người dùng) | Bộ nhớ Server (RAM hoặc Database) [1] |
| Dung lượng | Rất nhỏ (Tối đa tầm 4KB cho 1 file) | Không giới hạn (Tùy thuộc phần cứng Server) |
| Tính bảo mật | Thấp (Dễ bị người dùng xem hoặc sửa đổi) | Cao (Client chỉ thấy ID ngẫu nhiên, không thấy ruột) |
| Tốc độ | Nhanh hơn (Vì không tốn tài nguyên tìm kiếm) | Chậm hơn một chút (Server phải tra cứu dữ liệu) |
| Mục đích | Lưu cấu hình gọn nhẹ (Giao diện, ngôn ngữ…) | Lưu trạng thái nhạy cảm (Giỏ hàng, Đăng nhập) |
Lưu ý trong dự án thực tế khi dùng Session
Mặc định, express-session sẽ lưu toàn bộ dữ liệu session vào RAM của Server (MemoryStore). Điều này dẫn đến 2 thảm họa khi làm dự án thực tế:
- Nếu Server bị crash hoặc restart (ví dụ khi cập nhật code), toàn bộ người dùng đang đăng nhập sẽ bị văng ra ngoài vì RAM bị xóa sạch.
- Nếu bạn chạy nhiều server song song để chịu tải (Load Balancing), Server A sẽ không biết Session của khách hàng nằm ở Server B.
Giải pháp: Trong thực tế, lập trình viên sẽ cấu hình để lưu trữ Session vào một Database riêng biệt tốc độ cao, phổ biến nhất là Redis hoặc MongoDB thông qua các thư viện mở rộng như connect-redis hoặc connect-mongo.