T05 · Unauthorized Access and Privilege Escalation
- Location
project/backend/app/services/system_service.py:153- Finding
Stored API Key Exfiltration Through an Attacker-Controlled Model Endpoint
- Content
View full analysis
Dict: config = self.get_ai_model_config(config_id) if not config: return {"success": False, "message": "配置不存在"} try: if config.model_type == "online": from langchain_openai import ChatOpenAI llm = ChatOpenAI( openai_api_key=self._decrypt_api_key(config.api_key), openai_api_base=config.api_base_url, model=config.model_name, timeout=config.timeout ) response = llm.invoke("Hello") return {"success": True, "message": "连接成功", "response": str(response)} ``` The authorization middleware does not assign an administrative permission to system-management routes: ```python def _get_required_permission(self, path: str) -> str: if "/generate/" in path or "/case" in path: return "generate" elif "/execute/" in path or "/script/" in path: return "execute" else: return None ``` ### Technical Analysis The model API base URL is user-configurable, while the stored API key is decrypted and supplied to `ChatOpenAI` when the connection test runs. System-management routes require only a generally valid authorization code because `_get_required_permission()` returns `None`. An attacker can therefore change an existing model configuration's `api_base_url` without replacing its stored API key. Invoking the test endpoint causes the server to make an authenticated request to the attacker-controlled destination. The authorization header sent by the OpenAI-compatible client can expose the victim's model-provider credential. The ...[truncated 966 chars]- Remediation
View remediation
