From 62c92c298344158077e435f66004e3c1a81a70ee Mon Sep 17 00:00:00 2001 From: z30057876 Date: Tue, 2 Dec 2025 15:26:32 +0800 Subject: [PATCH 1/2] =?UTF-8?q?=E5=8E=BB=E9=99=A4=E5=86=97=E4=BD=99?= =?UTF-8?q?=E6=95=B0=E6=8D=AE=E7=BB=93=E6=9E=84=E3=80=81=E5=8E=BB=E9=99=A4?= =?UTF-8?q?API=E5=B7=A5=E5=85=B7=E5=AF=B9Token=E7=9A=84=E4=BE=9D=E8=B5=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/scheduler/call/api/api.py | 18 +----------------- apps/scheduler/pool/loader/mcp.py | 6 ++++-- apps/scheduler/pool/mcp/client.py | 9 ++------- apps/schemas/comment.py | 16 ---------------- apps/schemas/config.py | 29 ----------------------------- apps/schemas/flow.py | 8 -------- apps/schemas/mcp.py | 3 ++- apps/schemas/record.py | 14 +------------- apps/schemas/response_data.py | 13 ------------- 9 files changed, 10 insertions(+), 106 deletions(-) delete mode 100644 apps/schemas/comment.py diff --git a/apps/scheduler/call/api/api.py b/apps/scheduler/call/api/api.py index 1d064d000..654709182 100644 --- a/apps/scheduler/call/api/api.py +++ b/apps/scheduler/call/api/api.py @@ -12,7 +12,6 @@ from fastapi import status from pydantic import Field from pydantic.json_schema import SkipJsonSchema -from apps.common.auth import oidc_provider from apps.models import LanguageType from apps.scheduler.call.core import CoreCall from apps.schemas.enum_var import CallOutputType, ContentType, HTTPMethod @@ -23,7 +22,6 @@ from apps.schemas.scheduler import ( CallVars, ) from apps.services.service import ServiceCenterManager -from apps.services.token import TokenManager from .schema import APIInput, APIOutput @@ -173,7 +171,7 @@ class API(CoreCall, input_model=APIInput, output_model=APIOutput): async def _apply_auth(self) -> tuple[dict[str, str], dict[str, str], dict[str, str]]: """应用认证信息到请求参数中""" # self._auth可能是None或ServiceApiAuth类型 - # ServiceApiAuth类型包含header、cookie、query和oidc属性 + # ServiceApiAuth类型包含header、cookie、query属性 req_header = {} req_cookie = {} req_params = {} @@ -191,20 +189,6 @@ class API(CoreCall, input_model=APIInput, output_model=APIOutput): if self._auth.query: for item in self._auth.query: req_params[item.name] = item.value - # 如果oidc配置存在 - if self._service_id and self._auth.oidc: - if not self._user_id: - err = "[API] 未设置User ID" - _logger.error(err) - raise CallError(message=err, data={}) - - token = await TokenManager.get_plugin_token( - self._service_id, - self._user_id, - await oidc_provider.get_access_token_url(), - 30, - ) - req_header.update({"access-token": token}) return req_header, req_cookie, req_params diff --git a/apps/scheduler/pool/loader/mcp.py b/apps/scheduler/pool/loader/mcp.py index 0b1259e25..999fccbea 100644 --- a/apps/scheduler/pool/loader/mcp.py +++ b/apps/scheduler/pool/loader/mcp.py @@ -533,8 +533,10 @@ class MCPLoader: ) mcpsvc = mcp_config.mcpServers[mcp_id] - if mcp_env is not None: - mcp_config.mcpServers[mcp_id].env.update(mcp_env) + if mcp_env is not None and isinstance(mcpsvc, MCPServerStdioConfig): + mcpsvc.env.update(mcp_env) + elif mcp_env is not None and isinstance(mcpsvc, MCPServerSSEConfig): + mcpsvc.headers.update(mcp_env) if mcp_config.mcpType == MCPType.STDIO and isinstance(mcpsvc, MCPServerStdioConfig): index = None for i in range(len(mcpsvc.args)): diff --git a/apps/scheduler/pool/mcp/client.py b/apps/scheduler/pool/mcp/client.py index 3a2f5cb1f..d290add0d 100644 --- a/apps/scheduler/pool/mcp/client.py +++ b/apps/scheduler/pool/mcp/client.py @@ -55,10 +55,10 @@ class MCPClient: """ # 创建Client if isinstance(config, MCPServerSSEConfig): - env = config.env or {} + headers = config.headers or {} client = sse_client( url=config.url, - headers=env, + headers=headers, ) elif isinstance(config, MCPServerStdioConfig): if user_id: @@ -73,11 +73,6 @@ class MCPClient: env=config.env, cwd=cwd.as_posix(), )) - else: - self.error_sign.set() - err = f"[MCPClient] MCP {mcp_id}:未知的MCP服务类型“{config.type}”" - logger.error(err) - raise TypeError(err) # 创建Client、Session try: diff --git a/apps/schemas/comment.py b/apps/schemas/comment.py deleted file mode 100644 index 2191cba12..000000000 --- a/apps/schemas/comment.py +++ /dev/null @@ -1,16 +0,0 @@ -# Copyright (c) Huawei Technologies Co., Ltd. 2023-2025. All rights reserved. -"""评论相关的数据结构""" - -from pydantic import BaseModel, Field - -from apps.models import CommentType - - -class AddCommentData(BaseModel): - """添加评论""" - - record_id: str - comment: CommentType - dislike_reason: str = Field(default="", max_length=200) - reason_link: str = Field(default="", max_length=200) - reason_description: str = Field(default="", max_length=500) diff --git a/apps/schemas/config.py b/apps/schemas/config.py index 3ff43fd0a..18c8bef25 100644 --- a/apps/schemas/config.py +++ b/apps/schemas/config.py @@ -1,8 +1,6 @@ # Copyright (c) Huawei Technologies Co., Ltd. 2023-2025. All rights reserved. """配置文件数据结构""" -from typing import Literal - from pydantic import BaseModel, Field @@ -14,32 +12,6 @@ class DeployConfig(BaseModel): data_dir: str = Field(description="数据存储路径") -class OIDCConfig(BaseModel): - """AuthHub认证配置""" - - host: str = Field(description="OIDC服务路径") - host_inner: str = Field(description="OIDC服务路径(内网)") - login_api: str = Field(description="EulerCopilot登录API") - app_id: str = Field(description="OIDC AppID") - app_secret: str = Field(description="OIDC App Secret") - - -class FixedUserConfig(BaseModel): - """固定用户配置""" - - user_id: str = Field(description="禁用登录后,默认的用户ID") - - -class LoginConfig(BaseModel): - """OIDC配置""" - - provider: Literal[ - "authhub", "openeuler", "authelia", "disable", - ] = Field(description="OIDC Provider", default="authhub") - admin_user: list[str] = Field(description="管理员用户ID列表", default=[]) - settings: OIDCConfig | FixedUserConfig = Field(description="OIDC 配置") - - class RAGConfig(BaseModel): """RAG配置""" @@ -90,7 +62,6 @@ class ConfigModel(BaseModel): """配置文件的校验Class""" deploy: DeployConfig - login: LoginConfig rag: RAGConfig fastapi: FastAPIConfig minio: MinioConfig diff --git a/apps/schemas/flow.py b/apps/schemas/flow.py index 204e58f73..3b8264a7c 100644 --- a/apps/schemas/flow.py +++ b/apps/schemas/flow.py @@ -75,13 +75,6 @@ class MetadataBase(BaseModel): hashes: dict[str, str] | None = Field(description="资源(App、Service等)下所有文件的hash值", default=None) -class ServiceApiAuthOidc(BaseModel): - """Service的API鉴权方式的OIDC配置""" - - client_id: str = Field(description="OIDC客户端ID") - client_secret: str = Field(description="OIDC客户端密钥") - - class ServiceApiAuthKeyVal(BaseModel): """Service的API鉴权方式的键值对""" @@ -95,7 +88,6 @@ class ServiceApiAuth(BaseModel): header: list[ServiceApiAuthKeyVal] = Field(description="HTTP头鉴权配置", default=[]) cookie: list[ServiceApiAuthKeyVal] = Field(description="HTTP Cookie鉴权配置", default=[]) query: list[ServiceApiAuthKeyVal] = Field(description="HTTP URL参数鉴权配置", default=[]) - oidc: ServiceApiAuthOidc | None = Field(description="OIDC鉴权配置", default=None) class ServiceApiConfig(BaseModel): diff --git a/apps/schemas/mcp.py b/apps/schemas/mcp.py index c371cbbd8..78d995a52 100644 --- a/apps/schemas/mcp.py +++ b/apps/schemas/mcp.py @@ -32,7 +32,6 @@ class MCPContext(BaseModel): class MCPBasicConfig(BaseModel): """MCP 基本配置""" - env: dict[str, Any] = Field(description="MCP 服务器环境变量", default={}) autoApprove: list[str] = Field(description="自动批准的MCP权限列表", default=[]) # noqa: N815 autoInstall: bool = Field(description="是否自动安装MCP服务器", default=True) # noqa: N815 timeout: int = Field(description="MCP 服务器超时时间(秒)", default=60, alias="timeout") @@ -41,6 +40,7 @@ class MCPBasicConfig(BaseModel): class MCPServerStdioConfig(MCPBasicConfig): """MCP 服务器配置""" + env: dict[str, Any] = Field(description="MCP 服务器环境变量", default={}) command: str = Field(description="MCP 服务器命令") args: list[str] = Field(description="MCP 服务器命令参数") @@ -49,6 +49,7 @@ class MCPServerSSEConfig(MCPBasicConfig): """MCP 服务器配置""" url: str = Field(description="MCP 服务器地址", default="http://example.com/sse", pattern=r"^https?://.*$") + headers: dict[str, Any] = Field(description="MCP 服务器请求头", default={}) class MCPServerItem(BaseModel): diff --git a/apps/schemas/record.py b/apps/schemas/record.py index b48927f2e..7c8c17b50 100644 --- a/apps/schemas/record.py +++ b/apps/schemas/record.py @@ -2,12 +2,11 @@ """Record数据结构""" import uuid -from datetime import UTC, datetime from typing import Any, Literal from pydantic import BaseModel, Field -from apps.models import CommentType, StepStatus +from apps.models import StepStatus class RecordDocument(BaseModel): @@ -65,16 +64,6 @@ class RecordMetadata(BaseModel): time_cost: float = Field(default=0, alias="timeCost") -class RecordComment(BaseModel): - """Record表子项:Record的评论信息""" - - comment: CommentType = Field(default=CommentType.NONE) - feedback_type: list[str] = Field(default=[], alias="dislike_reason") - feedback_link: str = Field(default="", alias="reason_link") - feedback_content: str = Field(default="", alias="reason_description") - feedback_time: float = Field(default_factory=lambda: round(datetime.now(tz=UTC).timestamp(), 3)) - - class RecordData(BaseModel): """GET /api/record/{conversation_id} Result内元素数据结构""" @@ -85,5 +74,4 @@ class RecordData(BaseModel): flow: RecordExecutor | None = None content: RecordContent metadata: RecordMetadata - comment: CommentType = Field(default=CommentType.NONE) created_at: float = Field(alias="createdAt") diff --git a/apps/schemas/response_data.py b/apps/schemas/response_data.py index 2edc2ddc7..93541887c 100644 --- a/apps/schemas/response_data.py +++ b/apps/schemas/response_data.py @@ -46,19 +46,6 @@ class RecordListRsp(ResponseData): result: RecordListMsg - -class OidcRedirectMsg(BaseModel): - """GET /api/auth/redirect Result数据结构""" - - url: str - - -class OidcRedirectRsp(ResponseData): - """GET /api/auth/redirect 返回数据结构""" - - result: OidcRedirectMsg - - class ListTeamKnowledgeMsg(BaseModel): """GET /api/knowledge Result数据结构""" -- Gitee From 6635b1eace7615a6eca1f66ce97ef9f8ddf41fc3 Mon Sep 17 00:00:00 2001 From: z30057876 Date: Tue, 2 Dec 2025 15:36:26 +0800 Subject: [PATCH 2/2] =?UTF-8?q?=E5=8E=BB=E9=99=A4session=E6=A3=80=E6=9F=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/routers/appcenter.py | 3 +-- apps/routers/chat.py | 5 ++--- apps/routers/conversation.py | 3 +-- apps/routers/document.py | 3 +-- apps/routers/flow.py | 3 +-- apps/routers/llm.py | 4 +--- apps/routers/mcp_service.py | 4 +--- apps/routers/parameter.py | 3 +-- apps/routers/record.py | 4 +--- apps/routers/service.py | 3 --- apps/routers/tag.py | 3 +-- apps/routers/user.py | 8 ++++---- 12 files changed, 15 insertions(+), 31 deletions(-) diff --git a/apps/routers/appcenter.py b/apps/routers/appcenter.py index 646cd8a12..e14682957 100644 --- a/apps/routers/appcenter.py +++ b/apps/routers/appcenter.py @@ -9,7 +9,7 @@ from fastapi import APIRouter, Body, Depends, Path, Query, Request, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency.user import verify_personal_token, verify_session +from apps.dependency.user import verify_personal_token from apps.exceptions import InstancePermissionError from apps.models import AppType, PermissionType from apps.schemas.appcenter import ( @@ -39,7 +39,6 @@ router = APIRouter( prefix="/api/app", tags=["appcenter"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) diff --git a/apps/routers/chat.py b/apps/routers/chat.py index 1c1e19738..319a0845d 100644 --- a/apps/routers/chat.py +++ b/apps/routers/chat.py @@ -10,7 +10,7 @@ from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse, StreamingResponse from apps.common.queue import MessageQueue -from apps.dependency import verify_personal_token, verify_session +from apps.dependency import verify_personal_token from apps.models import ExecutorStatus from apps.scheduler.scheduler import Scheduler from apps.schemas.request_data import RequestData @@ -23,7 +23,6 @@ router = APIRouter( prefix="/api", tags=["chat"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) @@ -41,7 +40,7 @@ async def chat_generator(post_body: RequestData, user_id: str, auth_header: str) # 2. Scheduler初始化成功后,再设置用户处于活动状态 await Activity.set_active(user_id) - _logger.info(f"[Chat] 用户是否活跃: {await Activity.can_active(user_id)}") + _logger.info("[Chat] 用户是否活跃: %s", await Activity.can_active(user_id)) # 3. 最后判断并运行 Executor scheduler_task = asyncio.create_task(scheduler.run()) diff --git a/apps/routers/conversation.py b/apps/routers/conversation.py index 237a6b5b1..14825c6ee 100644 --- a/apps/routers/conversation.py +++ b/apps/routers/conversation.py @@ -9,7 +9,7 @@ from fastapi import APIRouter, Depends, Query, Request, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency import verify_personal_token, verify_session +from apps.dependency import verify_personal_token from apps.schemas.conversation import ( ChangeConversationData, ConversationListItem, @@ -28,7 +28,6 @@ router = APIRouter( prefix="/api/conversation", tags=["conversation"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) diff --git a/apps/routers/document.py b/apps/routers/document.py index 691e32023..d46e52324 100644 --- a/apps/routers/document.py +++ b/apps/routers/document.py @@ -9,7 +9,7 @@ from fastapi import APIRouter, Depends, Path, Request, UploadFile, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency import verify_personal_token, verify_session +from apps.dependency import verify_personal_token from apps.schemas.document import ( BaseDocumentItem, ConversationDocumentItem, @@ -31,7 +31,6 @@ router = APIRouter( prefix="/api/document", tags=["document"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) diff --git a/apps/routers/flow.py b/apps/routers/flow.py index 11bd2d359..dc9e9ca03 100644 --- a/apps/routers/flow.py +++ b/apps/routers/flow.py @@ -8,7 +8,7 @@ from fastapi import APIRouter, Body, Depends, Query, Request, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency import verify_personal_token, verify_session +from apps.dependency import verify_personal_token from apps.schemas.flow import ( FlowStructureDeleteMsg, FlowStructureDeleteRsp, @@ -28,7 +28,6 @@ router = APIRouter( prefix="/api/flow", tags=["flow"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) diff --git a/apps/routers/llm.py b/apps/routers/llm.py index a7567112b..3ab65eb15 100644 --- a/apps/routers/llm.py +++ b/apps/routers/llm.py @@ -7,7 +7,7 @@ from fastapi import APIRouter, Depends, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency import verify_admin, verify_personal_token, verify_session +from apps.dependency import verify_admin, verify_personal_token from apps.schemas.request_data import ( UpdateLLMReq, ) @@ -24,7 +24,6 @@ router = APIRouter( prefix="/api/llm", tags=["llm"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) @@ -32,7 +31,6 @@ admin_router = APIRouter( prefix="/api/llm", tags=["llm"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), Depends(verify_admin), ], diff --git a/apps/routers/mcp_service.py b/apps/routers/mcp_service.py index f6f021c62..e5145fd26 100644 --- a/apps/routers/mcp_service.py +++ b/apps/routers/mcp_service.py @@ -8,7 +8,7 @@ from fastapi import APIRouter, Depends, Path, Query, Request, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency.user import verify_admin, verify_personal_token, verify_session +from apps.dependency.user import verify_admin, verify_personal_token from apps.schemas.enum_var import SearchType from apps.schemas.mcp import ActiveMCPServiceRequest, UpdateMCPServiceRequest from apps.schemas.mcp_service import ( @@ -31,7 +31,6 @@ router = APIRouter( prefix="/api/mcp", tags=["mcp-service"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) @@ -39,7 +38,6 @@ admin_router = APIRouter( prefix="/api/admin/mcp", tags=["mcp-service"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), Depends(verify_admin), ], diff --git a/apps/routers/parameter.py b/apps/routers/parameter.py index ac9d5f216..febcb4d62 100644 --- a/apps/routers/parameter.py +++ b/apps/routers/parameter.py @@ -7,7 +7,7 @@ from fastapi import APIRouter, Depends, Request, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency.user import verify_personal_token, verify_session +from apps.dependency.user import verify_personal_token from apps.schemas.parameters import Type from apps.schemas.response_data import GetOperaRsp, GetParamsRsp from apps.services.appcenter import AppCenterManager @@ -19,7 +19,6 @@ router = APIRouter( tags=["parameter"], dependencies=[ Depends(verify_personal_token), - Depends(verify_session), ], ) diff --git a/apps/routers/record.py b/apps/routers/record.py index 2700ca953..b581f022a 100644 --- a/apps/routers/record.py +++ b/apps/routers/record.py @@ -10,8 +10,7 @@ from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse from apps.common.security import Security -from apps.dependency import verify_personal_token, verify_session -from apps.models import ExecutorHistory +from apps.dependency import verify_personal_token from apps.schemas.record import ( RecordContent, RecordData, @@ -33,7 +32,6 @@ router = APIRouter( prefix="/api/record", tags=["record"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) diff --git a/apps/routers/service.py b/apps/routers/service.py index e2fa4ff14..763937fae 100644 --- a/apps/routers/service.py +++ b/apps/routers/service.py @@ -12,7 +12,6 @@ from fastapi.responses import JSONResponse from apps.dependency.user import ( verify_admin, verify_personal_token, - verify_session, ) from apps.exceptions import InstancePermissionError from apps.schemas.enum_var import SearchType @@ -38,7 +37,6 @@ router = APIRouter( prefix="/api/service", tags=["service-center"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), ], ) @@ -46,7 +44,6 @@ admin_router = APIRouter( prefix="/api/admin/service", tags=["service-center"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), Depends(verify_admin), ], diff --git a/apps/routers/tag.py b/apps/routers/tag.py index 7affdee22..ab764a291 100644 --- a/apps/routers/tag.py +++ b/apps/routers/tag.py @@ -5,7 +5,7 @@ from fastapi import APIRouter, Depends, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.dependency.user import verify_admin, verify_personal_token, verify_session +from apps.dependency.user import verify_admin, verify_personal_token from apps.schemas.request_data import PostTagData from apps.schemas.response_data import ResponseData from apps.services.tag import TagManager @@ -14,7 +14,6 @@ admin_router = APIRouter( prefix="/api/tag", tags=["tag"], dependencies=[ - Depends(verify_session), Depends(verify_personal_token), Depends(verify_admin), ], diff --git a/apps/routers/user.py b/apps/routers/user.py index 01fc885c4..5e17482cf 100644 --- a/apps/routers/user.py +++ b/apps/routers/user.py @@ -5,8 +5,8 @@ from fastapi import APIRouter, Depends, Request, status from fastapi.encoders import jsonable_encoder from fastapi.responses import JSONResponse -from apps.common.config import config -from apps.dependency import verify_personal_token, verify_session +from apps.dependency import verify_personal_token +from apps.dependency.user import is_admin from apps.schemas.request_data import UserUpdateRequest from apps.schemas.response_data import ResponseData from apps.schemas.tag import UserTagListResponse @@ -17,7 +17,7 @@ from apps.services.user_tag import UserTagManager router = APIRouter( prefix="/api/user", tags=["user"], - dependencies=[Depends(verify_session), Depends(verify_personal_token)], + dependencies=[Depends(verify_personal_token)], ) @@ -59,7 +59,7 @@ async def get_user_info(request: Request) -> JSONResponse: user_info = UserInfoMsg( userId=user.id, userName=user.userName, - isAdmin=user.id in config.login.admin_user, + isAdmin=is_admin(user.userName), personalToken=user.personalToken, autoExecute=user.autoExecute or False, ) -- Gitee