2009-10-13 32 views
5

Trước đây, tôi đã luôn sử dụngCác truy vấn PHP MySQLi được chuẩn bị với các tham số ràng buộc có an toàn không?

mysql_real_escape_string() 

cho tất cả đầu vào có nguồn gốc từ người dùng cuối cùng sẽ chạm vào cơ sở dữ liệu.

Bây giờ tôi đã chuyển đổi hoàn toàn sang MySQLi và tôi đang sử dụng các truy vấn đã chuẩn bị với các tham số ràng buộc, tôi đã loại bỏ khả năng tấn công SQL injection có hiệu quả không?

Tôi thích hợp trong nói rằng tôi không còn cần

mysql_real_escape_string()? 

Đây là hiểu biết của tôi và cơ sở của một dự án của tôi: http://sourceforge.net/projects/mysqldoneright/files/Base/MysqlDoneRight-0.23.tar.gz/download

Đây không phải là điều mà tôi muốn nhận sai mặc dù như bây giờ tôi đã phát hành nó, nó cũng có thể ảnh hưởng đến người khác.

Tất cả thông tin nhập do người dùng cung cấp giờ đây sẽ kết thúc bằng bind_parms.
Các truy vấn được cung cấp trong giai đoạn chuẩn bị là tĩnh.

Trả lời

6

Nó không đơn giản như vậy. Bạn có thể sử dụng các tham số ràng buộc thay vì suy biến ứng dụng vào biểu SQL thay giá trị theo nghĩa đen chỉ:

$sql = "SELECT * FROM MyTable WHERE id = ".$_GET["id"]; // not safe 

$sql = "SELECT * FROM MyTable WHERE id = ?"; // safe 

Nhưng nếu bạn cần phải thực hiện một phần của truy vấn năng động bên cạnh một giá trị văn chương?

$sql = "SELECT * FROM MyTable ORDER BY ".$_GET["sortcolumn"]; // not safe 

$sql = "SELECT * FROM MyTable ORDER BY ?"; // doesn't work! 

Thông số này sẽ luôn được hiểu là giá trị, không phải là số nhận dạng cột. Bạn có thể chạy truy vấn với ORDER BY 'score', khác với ORDER BY score và sử dụng thông số sẽ được hiểu là thông số trước - một chuỗi không đổi 'score', không phải giá trị trong cột có tên score.

Vì vậy, có rất nhiều trường hợp bạn phải sử dụng SQL động và nội suy biến ứng dụng vào truy vấn để nhận được kết quả mong muốn. Trong những trường hợp đó, tham số truy vấn không thể giúp bạn. Bạn vẫn phải cảnh giác và bảo vệ mã để ngăn ngừa lỗi SQL injection.

Không có thư viện khung hoặc truy cập dữ liệu nào có thể làm việc này cho bạn. Bạn luôn có thể xây dựng một chuỗi truy vấn SQL có chứa một lỗ hổng SQL injection, và bạn làm điều này trước khi thư viện truy cập dữ liệu nhìn thấy truy vấn SQL. Vì vậy, làm thế nào là nó phải biết những gì là cố ý và những gì một lỗ hổng?

Sau đây là các phương pháp để đạt các truy vấn SQL an toàn:

  • Lọc đầu vào. Theo dõi bất kỳ dữ liệu biến nào được chèn vào truy vấn SQL của bạn. Sử dụng dữ liệu nhập filters để loại bỏ các ký tự không hợp lệ.Ví dụ, nếu bạn mong đợi một số nguyên, hãy chắc chắn rằng đầu vào bị ràng buộc là một số nguyên.

  • Đầu ra thoát. Đầu ra trong ngữ cảnh này có thể là truy vấn SQL mà bạn gửi đến máy chủ cơ sở dữ liệu. Bạn biết bạn có thể sử dụng các tham số truy vấn SQL cho các giá trị, nhưng về tên cột thì sao? Bạn cần một chức năng thoát/trích dẫn cho các số nhận dạng, giống như số mysql_real_escape_string() cũ là dành cho các giá trị chuỗi.

  • Đánh giá mã. Làm cho ai đó trở thành cặp mắt thứ hai và xem lại mã SQL của bạn, để giúp bạn phát hiện ra những nơi mà bạn bỏ qua để sử dụng hai kỹ thuật trên.

+0

Vâng. Nhận thấy rằng bạn không thể làm ORDER BY? bit với các tham số. Câu trả lời tốt. –

+0

Tôi nhận được phiếu giảm giá? Downvoter, bạn nên mô tả lý do tại sao bạn nghĩ rằng câu trả lời này là không thỏa đáng. Có lẽ tôi có thể cải thiện nó. –

13

Có. Sử dụng truy vấn đã chuẩn bị sẽ thoát khỏi các tham số.

+0

Ngắn, ngọt và chính xác. – ceejayoz

+0

Cảm ơn. Chỉ muốn chắc chắn rằng tôi đã không bỏ lỡ điều gì đó hiển nhiên. Tôi có xu hướng làm điều đó. –

1

Khi bạn liên kết các tham số với câu lệnh đã chuẩn bị, nó sẽ tự động thoát khỏi dữ liệu, vì vậy bạn không nên thoát khỏi nó trước khi gửi nó. Thoát kép thường là một điều xấu. Ít nhất, nó tạo ra kết quả xấu xí với các ký tự thoát sau này.

Các vấn đề liên quan