Dự án này minh họa sự khác biệt giữa cách truy vấn cơ sở dữ liệu an toàn và không an toàn trong FastAPI, đặc biệt tập trung vào lỗ hổng SQL Injection.
Ứng dụng FastAPI này cung cấp hai endpoint:
- Endpoint an toàn: Sử dụng parameter binding để tránh SQL injection
- Endpoint không an toàn: Sử dụng string concatenation, dễ bị tấn công SQL injection
- Python 3.12 hoặc cao hơn
- Conda hoặc pip để quản lý package
-
Tạo môi trường từ file environment.yml:
conda env create -f environment.yml
-
Kích hoạt môi trường:
conda activate demo
-
Chạy ứng dụng:
python app.py
-
Tạo môi trường conda mới rỗng:
conda create -n demo python=3.12
-
Kích hoạt môi trường:
conda activate demo
-
Cài đặt dependencies bằng pip:
pip install -r requirements.txt
-
Chạy ứng dụng:
python app.py
Dự án sử dụng SQLite với bảng students:
| Cột | Kiểu dữ liệu | Mô tả |
|---|---|---|
| id | INTEGER PRIMARY KEY | ID sinh viên (tự động tăng) |
| name | TEXT | Tên sinh viên |
| age | INTEGER | Tuổi sinh viên |
Dữ liệu mẫu:
- ID: 1, Tên: Alice, Tuổi: 20
- ID: 2, Tên: Bob, Tuổi: 22
Sau khi chạy ứng dụng, truy cập: http://localhost:8000
GET /
Mô tả:
- Kiểm tra xem API có hoạt động hay không
- Trả về thông báo xác nhận
Response:
{
"message": "API is working!"
}GET /students/{student_id}
Ví dụ:
GET /students/1- Lấy thông tin sinh viên ID = 1
Đặc điểm:
- ✅ Sử dụng parameter binding
- ✅ An toàn khỏi SQL injection
- ✅ Validate input là số nguyên
GET /students-unsafe/?student_id={id}
Ví dụ:
- Truy vấn bình thường:
GET /students-unsafe/?student_id=1 - SQL Injection:
GET /students-unsafe/?student_id=1 OR 1=1
- ❌ Dễ bị tấn công SQL injection
- ❌ Không validate input
- ❌ Chỉ sử dụng cho mục đích học tập
GET /students-unsafe/?student_id=1
SQL được thực thi: SELECT name, age FROM students WHERE id = 1
GET /students-unsafe/?student_id=1 OR 1=1
SQL được thực thi: SELECT name, age FROM students WHERE id = 1 OR 1=1
Điều này sẽ trả về tất cả sinh viên trong database thay vì chỉ một sinh viên cụ thể.
FastAPI tự động tạo documentation:
- Swagger UI:
http://localhost:8000/docs - ReDoc:
http://localhost:8000/redoc
cursor.execute("SELECT name, age FROM students WHERE id = ?", (student_id,))query = f"SELECT name, age FROM students WHERE id = {student_id_str}"
cursor.execute(query)Demo_SQL_Injection/
├── app.py # Ứng dụng FastAPI chính
├── students.db # Cơ sở dữ liệu SQLite
├── environment.yml # Conda environment file
├── requirements.txt # Python dependencies
└── README.md # Tài liệu dự án
- FastAPI: Web framework hiện đại cho Python
- Uvicorn: ASGI server để chạy FastAPI
- SQLite3: Database engine (built-in Python)
- Pydantic: Data validation và serialization
Dự án này được tạo ra để:
- Hiểu rõ SQL Injection: Cách thức hoạt động và tác hại
- Học cách phòng chống: Sử dụng parameter binding
- Thực hành FastAPI: Tạo API endpoints an toàn
- So sánh phương pháp: An toàn vs không an toàn
- KHÔNG BAO GIỜ sử dụng endpoint không an toàn trong production
- Endpoint
/students-unsafe/chỉ dành cho mục đích demo và học tập - Luôn sử dụng parameter binding khi làm việc với database
- Validate và sanitize tất cả input từ người dùng
Dự án này được tạo ra cho mục đích giáo dục và có thể sử dụng tự do.
Tác giả: cuongphamduc
Thời gian tạo: 2025
Mục đích: Giáo dục về SQL Injection Security