Tổng quan
Hệ thống mô phỏng bệnh nhân ảo cho giáo dục y khoa. Sử dụng LLM kết hợp RAG (Retrieval-Augmented Generation) để tạo ra các ca bệnh thực tế, hỗ trợ sinh viên và bác sĩ thực hành hội chẩn, chẩn đoán, và điều trị.
Công nghệ
| Framework | FastAPI (Python) |
| LLM | Google Gemma 4 (gemma4_service) |
| RAG | Retrieval-Augmented Generation từ patient_data/ |
| Data Source | File JSON trong patient_data/ |
| Port | 8025 (FastAPI), proxy: 443 |
| Base URL (public) | https://pnt.badt.vn/virtualpatient/ |
Base URL
https://pnt.badt.vn/virtualpatient
External: https://dv.badt.vn/ai/virtualpatient/ | Internal: http://localhost:8025
Xác thực
API này yêu cầu Bearer token trong Authorization header. Liên hệ admin để nhận API token.
Cách dùng
Authorization: Bearer YOUR_API_TOKEN
- Không chia sẻ token công khai hoặc commit vào source code
- Dùng environment variables để lưu token
- Admin endpoints yêu cầu token có quyền admin
API Endpoints
/
Root info — trả về thông tin service cơ bản.
Example Response
{
"message": "Medical Patient Simulator RAG System",
"status": "running",
"version": "1.0.0"
}
/ui
Web UI — giao diện người dùng trên trình duyệt.
/health
Health check cơ bản — trả về trạng thái service và các thành phần.
Example Response
{
"status": "healthy",
"llm_provider": "gemma4",
"llm_client_initialized": true,
"rag_system_initialized": true,
"llm_api_status": "healthy",
"model": "google/gemma-2-9b-it"
}
/health/deep
Deep health check — kiểm tra chi tiết: LLM latency, patient files, disk usage, uptime.
Example Response
{
"status": "healthy",
"request_id": "a87a88de",
"llm_latency_ms": 2.13,
"model": "google/gemma-2-9b-it",
"patient_files_count": 0,
"patient_data_disk_usage_mb": 2.6,
"uptime_human": "0h 27m 28s"
}
/chat
Chat với bệnh nhân ảo. Đây là endpoint chính cho tương tác hội thoại.
Request body
{
"message": "Bệnh nhân có triệu chứng gì?",
"patient_id": "benhnhan001",
"session_id": "session-uuid-v4",
"language": "vi"
}
Example Response
{
"response": "Tôi bị đau đầu nhiều, kèm sốt nhẹ và mệt mỏi...",
"patient_id": "benhnhan001",
"session_id": "session-uuid-v4",
"patient_info": {
"name": "Nguyễn Văn A",
"age": 45,
"diagnosis": "Tăng huyết áp"
}
}
/chat-optimized
Chat optimized — phiên bản tối ưu, nhanh hơn cho chat thông thường.
Request body (giống /chat)
{
"message": "Xin chào bác sĩ!",
"patient_id": "benhnhan001",
"session_id": "session-uuid-v4",
"language": "vi"
}
/clinical-data/{patient_id}
Lấy dữ liệu lâm sàng đầy đủ của bệnh nhân theo ID.
Path Parameters
patient_id | string (required) | ID của bệnh nhân |
Example
curl https://pnt.badt.vn/virtualpatient/clinical-data/benhnhan001 \
-H "Authorization: Bearer YOUR_API_TOKEN"
/clinical-data/{patient_id}/summary
Tóm tắt hồ sơ bệnh nhân — bản rút gọn các thông tin quan trọng.
Path Parameters
patient_id | string (required) | ID của bệnh nhân |
/prompt-config
Lấy cấu hình prompt hiện tại của hệ thống.
/prompt-config
Cập nhật cấu hình prompt.
Request body
{
"system_prompt": "Bạn là bệnh nhân ảo...",
"temperature": 0.7,
"max_tokens": 500
}
/patients
Liệt kê tất cả bệnh nhân có trong hệ thống.
Example Response
{
"patients": [
{
"id": "benhnhan001",
"name": "Nguyễn Văn A",
"age": 45,
"diagnosis": "Tăng huyết áp"
}
],
"total": 1
}
/voice-interaction
Tương tác giọng nói với bệnh nhân ảo. Gửi file audio, nhận response text kèm tư vấn.
Request (multipart/form-data)
audio | file (required) | File audio (.wav, .mp3, .ogg) |
patient_id | string (required) | ID bệnh nhân |
Example (cURL)
curl -X POST https://pnt.badt.vn/virtualpatient/voice-interaction \
-H "Authorization: Bearer YOUR_API_TOKEN" \
-F "audio=@/path/to/question.wav" \
-F "patient_id=benhnhan001"
/admin/files
Quản lý file admin — liệt kê các file trong thư mục admin.
/admin/read-file
Đọc nội dung file từ server.
Query Parameters
file_path | string (required) | Đường dẫn file |
/admin/save-file
Ghi nội dung vào file trên server.
Request body
{
"file_path": "...",
"content": "Nội dung file..."
}
/admin/delete-file
Xóa file trên server.
Request body
{
"file_path": "..."
}
Chat với bệnh nhân ảo
Tương tác với bệnh nhân ảo qua text. Hệ thống sử dụng RAG để lấy thông tin từ hồ sơ bệnh nhân, sau đó LLM tạo ra câu trả lời phù hợp với vai trò và bệnh cảnh.
Cơ chế hoạt động
- Nhận message + patient_id
- RAG truy xuất thông tin bệnh nhân từ file JSON
- LLM sinh câu trả lời dựa trên context (bệnh sử, triệu chứng, tuổi, giới...)
- Trả về response kèm patient_info
Ví dụ Python
import requests
import os
url = "https://pnt.badt.vn/virtualpatient/chat"
headers = {
"Authorization": f"Bearer {os.getenv('API_AI_TOKEN')}",
"Content-Type": "application/json"
}
data = {
"message": "Chào bác sĩ, tôi bị đau bụng từ sáng",
"patient_id": "benhnhan001",
"language": "vi"
}
response = requests.post(url, json=data, headers=headers)
result = response.json()
print(result["response"])
Ví dụ cURL
curl -X POST https://pnt.badt.vn/virtualpatient/chat \
-H "Authorization: Bearer YOUR_API_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"message": "Bệnh nhân có tiền sử bệnh gì?",
"patient_id": "benhnhan001",
"language": "vi"
}'
Clinical Data & Patient Summary
Truy xuất thông tin chi tiết của bệnh nhân từ hệ thống RAG.
1. Lấy dữ liệu lâm sàng đầy đủ
curl https://pnt.badt.vn/virtualpatient/clinical-data/benhnhan001 \
-H "Authorization: Bearer YOUR_API_TOKEN"
2. Lấy tóm tắt bệnh nhân
curl https://pnt.badt.vn/virtualpatient/clinical-data/benhnhan001/summary \
-H "Authorization: Bearer YOUR_API_TOKEN"
Ví dụ Python
import requests
import os
token = os.getenv("API_AI_TOKEN")
headers = {"Authorization": f"Bearer {token}"}
# Full clinical data
resp = requests.get(
"https://pnt.badt.vn/virtualpatient/clinical-data/benhnhan001",
headers=headers
)
print(resp.json())
# Summary
resp = requests.get(
"https://pnt.badt.vn/virtualpatient/clinical-data/benhnhan001/summary",
headers=headers
)
print(resp.json())
Quản lý bệnh nhân
Liệt kê và quản lý danh sách bệnh nhân trong hệ thống.
Danh sách tất cả bệnh nhân
curl https://pnt.badt.vn/virtualpatient/patients \
-H "Authorization: Bearer YOUR_API_TOKEN"
Lưu ý
- Mỗi bệnh nhân có một file JSON riêng trong thư mục
patient_data/ - File JSON chứa: thông tin nhân khẩu, bệnh sử, tiền sử, thuốc, xét nghiệm...
- Khi thêm bệnh nhân mới, cần tạo file JSON tương ứng
- Hệ thống RAG tự động index dữ liệu bệnh nhân
Voice Interaction
Gửi câu hỏi dạng audio, server thực hiện: Speech-to-Text → RAG + LLM → Text-to-Speech. Kết quả trả về gồm text và audio.
Cơ chế
- Upload file audio (câu hỏi của bác sĩ/sinh viên)
- Medical Transcribe service chuyển audio → text
- RAG truy xuất thông tin bệnh nhân
- LLM sinh câu trả lời
- Text-to-Speech chuyển response → audio
- Trả về cả text và audio
Ví dụ Python
import requests
import os
files = {
"audio": ("question.wav", open("question.wav", "rb"), "audio/wav")
}
data = {"patient_id": "benhnhan001"}
response = requests.post(
"https://pnt.badt.vn/virtualpatient/voice-interaction",
headers={"Authorization": f"Bearer {os.getenv('API_AI_TOKEN')}"},
files=files,
data=data
)
result = response.json()
print("Response text:", result["response"])
# If audio returned, save it
if "audio" in result:
with open("doctor_response.wav", "wb") as f:
f.write(result["audio"])
Định dạng audio hỗ trợ
| Input | WAV, MP3, OGG (16kHz mono khuyến nghị) |
| Output | WAV (PCM 16-bit, dùng Text2Speech service) |
| Max file size | 25 MB |
Cấu trúc Patient Data (JSON)
Mỗi bệnh nhân là một file JSON trong patient_data/. Cấu trúc mẫu:
{
"patient_id": "benhnhan001",
"name": "Nguyễn Văn A",
"age": 45,
"gender": "nam",
"diagnosis": "Tăng huyết áp giai đoạn 2",
"medical_history": "Tăng huyết áp 5 năm, đái tháo đường type 2",
"symptoms": "Đau đầu, chóng mặt, mệt mỏi",
"medications": ["Amlodipine 5mg", "Metformin 500mg"],
"allergies": ["Penicillin"],
"test_results": {
"blood_pressure": "160/95 mmHg",
"blood_sugar": "7.2 mmol/L",
"cholesterol": "6.8 mmol/L"
},
"lifestyle": {
"smoking": false,
"alcohol": "social",
"exercise": "ít vận động"
}
}
Thư mục chứa dữ liệu bệnh nhân: /đường_dẫn_project/patient_data/. Hệ thống tự động quét và index tất cả file JSON khi khởi động.
Admin File Management
Các endpoint admin yêu cầu token có quyền admin. Sử dụng cẩn thận vì có thể đọc/ghi/xóa file tùy ý trên server.
List files
curl https://pnt.badt.vn/virtualpatient/admin/files \
-H "Authorization: Bearer ADMIN_API_TOKEN"
Read file
curl "https://pnt.badt.vn/virtualpatient/admin/read-file?file_path=/path/to/file" \
-H "Authorization: Bearer ADMIN_API_TOKEN"
Save file
curl -X POST https://pnt.badt.vn/virtualpatient/admin/save-file \
-H "Authorization: Bearer ADMIN_API_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"file_path": "/path/to/file.json",
"content": "{\"key\": \"value\"}"
}'
Delete file
curl -X DELETE https://pnt.badt.vn/virtualpatient/admin/delete-file \
-H "Authorization: Bearer ADMIN_API_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"file_path": "/path/to/delete.json"
}'
Error Codes
| Code | Error | Description |
|---|---|---|
400 |
Bad Request | Tham số request không hợp lệ |
401 |
Unauthorized | Bearer token thiếu hoặc không hợp lệ |
404 |
Not Found | Patient ID không tồn tại |
422 |
Validation Error | Request validation failed |
500 |
Internal Server Error | Lỗi LLM hoặc RAG service |
503 |
Service Unavailable | LLM hoặc RAG backend chưa sẵn sàng |
504 |
Gateway Timeout | Request timeout (>60s) |