Giới thiệu
MySQL không cho phép dùng biến trực tiếp làm tên cột trong SELECT. Để chọn cột động, cần xây dựng chuỗi truy vấn động và thực thi qua PREPARED STATEMENT.
Ví dụ minh họa
Tạo bảng và chèn dữ liệu
mysql> CREATE TABLE DemoTable (
EmployeeName VARCHAR(100)
);
mysql> INSERT INTO DemoTable VALUES ('John Doe');
Các bước thực hiện
-- 1. Tạo chuỗi truy vấn động
SET @dynamicQuery = CONCAT("SELECT ", (SELECT "EmployeeName FROM DemoTable"));
-- 2. Xem truy vấn đã tạo
SELECT @dynamicQuery;
-- Kết quả: SELECT EmployeeName FROM DemoTable
-- 3. Chuẩn bị statement
PREPARE myStatement FROM @dynamicQuery;
-- 4. Thực thi
EXECUTE myStatement;
-- 5. Giải phóng (tùy chọn nhưng khuyến nghị)
DEALLOCATE PREPARE myStatement;
Kết quả
+--------------+ | EmployeeName | +--------------+ | John Doe | +--------------+
Ứng dụng thực tế
Thường dùng khi tên cột được truyền từ ứng dụng (PHP, Java, Python...) hoặc quyết định tại runtime.
-- Ví dụ: Chọn cột dựa trên tham số
SET @colName = 'EmployeeName'; -- Giả sử lấy từ biến
SET @sql = CONCAT('SELECT `', @colName, '` FROM DemoTable');
PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;
⚠️ Cảnh báo bảo mật
SQL Injection: Không bao giờ nối trực tiếp đầu vào người dùng vào chuỗi truy vấn không qua kiểm tra/escape. Luôn validate tên cột đối với danh sách cho phép (whitelist).
Lưu ý
- Prepared statement chỉ tồn tại trong session hiện tại.
- Không thể dùng PREPARE trong stored function/trigger (chỉ trong procedure).
- Tên cột/table nên bao quanh bằng backtick
`để an toàn.