-
Notifications
You must be signed in to change notification settings - Fork 0
Adds LLM-based test case generation API endpoints #195
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: dev
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,352 @@ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| """ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| LLM Test Data Generation Service | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| 封裝與 LLM 測資生成服務的 API 互動邏輯 | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| """ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| import requests | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| import logging | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| from io import BytesIO | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| from typing import Optional, List, Dict, Any | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| from django.conf import settings | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| logger = logging.getLogger(__name__) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| # LLM 測資生成服務設定 | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| LLM_TESTGEN_API_URL = getattr(settings, 'LLM_TESTGEN_API_URL', 'http://34.81.90.111:8001') | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| LLM_TESTGEN_API_URL = getattr(settings, 'LLM_TESTGEN_API_URL', 'http://34.81.90.111:8001') | |
| LLM_TESTGEN_API_URL = getattr(settings, 'LLM_TESTGEN_API_URL', 'http://localhost:8001') |
Copilot
AI
Dec 28, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The LLM service URL should be validated when loaded from settings. If the URL is malformed or points to an invalid location, requests will fail with unclear errors. Consider adding validation to ensure the URL is properly formatted and optionally check service availability on startup.
| logger = logging.getLogger(__name__) | |
| # LLM 測資生成服務設定 | |
| LLM_TESTGEN_API_URL = getattr(settings, 'LLM_TESTGEN_API_URL', 'http://34.81.90.111:8001') | |
| from urllib.parse import urlparse | |
| logger = logging.getLogger(__name__) | |
| # LLM 測資生成服務設定 | |
| DEFAULT_LLM_TESTGEN_API_URL = 'http://34.81.90.111:8001' | |
| def _validate_llm_service_url(url: str) -> str: | |
| """ | |
| 驗證並標準化 LLM 服務的基底 URL。 | |
| 如果設定的 URL 無效,會記錄警告並回退到預設值。 | |
| """ | |
| if not url: | |
| logger.warning( | |
| "LLM_TESTGEN_API_URL is empty or not set; falling back to default '%s'.", | |
| DEFAULT_LLM_TESTGEN_API_URL, | |
| ) | |
| return DEFAULT_LLM_TESTGEN_API_URL | |
| parsed = urlparse(url) | |
| if parsed.scheme not in ("http", "https") or not parsed.netloc: | |
| logger.warning( | |
| "Invalid LLM_TESTGEN_API_URL '%s'; falling back to default '%s'.", | |
| url, | |
| DEFAULT_LLM_TESTGEN_API_URL, | |
| ) | |
| return DEFAULT_LLM_TESTGEN_API_URL | |
| # 移除結尾的斜線以避免組 URL 時出現重複的 '/' | |
| return url.rstrip("/") | |
| LLM_TESTGEN_API_URL = _validate_llm_service_url( | |
| getattr(settings, 'LLM_TESTGEN_API_URL', DEFAULT_LLM_TESTGEN_API_URL) | |
| ) |
Copilot
AI
Dec 28, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The JavaScript to Python fallback for unsupported languages is problematic. It silently converts JavaScript code to be executed as Python, which will likely fail during execution. Instead, this should return an error indicating that the language is not supported by the LLM service.
Copilot
AI
Dec 28, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The code logs the full API response payload which may contain sensitive information or large data that could flood logs. Consider using logger.debug for detailed payload logging rather than logger.info, and potentially sanitize or truncate the logged data.
| logger.info(f'Upload solution response: {result}') | |
| # Log the response payload in debug level and truncate to avoid flooding logs | |
| result_str = str(result) | |
| max_log_length = 1000 | |
| if len(result_str) > max_log_length: | |
| result_str = result_str[:max_log_length] + '... [truncated]' | |
| logger.debug(f'Upload solution response: {result_str}') |
Copilot
AI
Dec 28, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The Problem_subtasks model has 'description' as a potential field based on its usage pattern in the service (line 288), but this field doesn't exist in the model definition. The model only has 'weight', 'time_limit_ms', 'memory_limit_mb', and timestamp fields. This will cause an AttributeError at runtime.
| 'desc': st.description or '', | |
| 'desc': getattr(st, 'description', '') or '', |
Copilot
AI
Dec 28, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The attribute 'num_testcases' doesn't exist in the Problem_subtasks model. According to the model definition, Problem_subtasks only has fields like 'weight', 'time_limit_ms', and 'memory_limit_mb'. This hasattr check will always return False, and the fallback to 5 will always be used. Either add this field to the model or determine the number of test cases differently.
| 'num': st.num_testcases if hasattr(st, 'num_testcases') else 5 | |
| 'num': 5 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The hardcoded IP address 'http://34.81.90.111:8001' in the default configuration is a security and maintainability concern. This appears to be a production IP address that should not be hardcoded in the codebase. Consider using 'localhost' or an empty string as the default, and require explicit configuration via environment variables in production.