[add] app chat v1
This commit is contained in:
@@ -1,35 +1,32 @@
|
||||
from sqlalchemy.orm import Session
|
||||
from typing import List, Optional
|
||||
import uuid
|
||||
import secrets
|
||||
import hashlib
|
||||
import datetime
|
||||
from fastapi import HTTPException, status
|
||||
import hashlib
|
||||
import secrets
|
||||
import uuid
|
||||
from os import getenv
|
||||
from typing import List, Optional
|
||||
|
||||
from sqlalchemy.orm import Session
|
||||
|
||||
from app.core.config import settings
|
||||
from app.core.error_codes import BizCode
|
||||
from app.core.exceptions import BusinessException, PermissionDeniedException
|
||||
from app.models.tenant_model import Tenants
|
||||
from app.core.logging_config import get_business_logger
|
||||
from app.models.user_model import User
|
||||
from app.models.app_model import App
|
||||
from app.models.end_user_model import EndUser
|
||||
from app.models.workspace_model import Workspace, WorkspaceRole, WorkspaceInvite, InviteStatus, WorkspaceMember
|
||||
from app.models.workspace_model import Workspace, WorkspaceRole, InviteStatus, WorkspaceMember
|
||||
from app.repositories import workspace_repository
|
||||
from app.repositories.workspace_invite_repository import WorkspaceInviteRepository
|
||||
from app.schemas.workspace_schema import (
|
||||
WorkspaceCreate,
|
||||
WorkspaceUpdate,
|
||||
WorkspaceInviteCreate,
|
||||
WorkspaceCreate,
|
||||
WorkspaceUpdate,
|
||||
WorkspaceInviteCreate,
|
||||
WorkspaceInviteResponse,
|
||||
InviteValidateResponse,
|
||||
InviteAcceptRequest,
|
||||
WorkspaceMemberUpdate
|
||||
)
|
||||
from app.repositories import workspace_repository
|
||||
from app.repositories.workspace_invite_repository import WorkspaceInviteRepository
|
||||
from app.core.logging_config import get_business_logger
|
||||
from app.core.config import settings
|
||||
from app.services import user_service
|
||||
from os import getenv
|
||||
|
||||
# 获取业务逻辑专用日志器
|
||||
business_logger = get_business_logger()
|
||||
import os #
|
||||
from dotenv import load_dotenv
|
||||
load_dotenv()
|
||||
def switch_workspace(
|
||||
@@ -39,10 +36,10 @@ def switch_workspace(
|
||||
):
|
||||
"""切换工作空间"""
|
||||
business_logger.debug(f"用户 {user.username} 请求切换工作空间为 {workspace_id}")
|
||||
|
||||
|
||||
# 检查用户是否为成员或超级管理员
|
||||
_check_workspace_member_permission(db, workspace_id, user)
|
||||
|
||||
|
||||
# 更新当前用户的工作空间上下文
|
||||
try:
|
||||
user.current_workspace_id = workspace_id
|
||||
@@ -63,22 +60,22 @@ def delete_workspace_member(
|
||||
):
|
||||
"""删除工作空间成员"""
|
||||
business_logger.debug(f"用户 {user.username} 请求删除工作空间 {workspace_id} 的成员 {member_id}")
|
||||
_check_workspace_admin_permission(db, workspace_id, user)
|
||||
_check_workspace_admin_permission(db, workspace_id, user)
|
||||
workspace_member = workspace_repository.get_member_by_id(db=db, member_id=member_id)
|
||||
if not workspace_member:
|
||||
raise BusinessException(f"工作空间成员 {member_id} 不存在", BizCode.WORKSPACE_MEMBER_NOT_FOUND)
|
||||
|
||||
|
||||
if workspace_member.workspace_id != workspace_id:
|
||||
raise BusinessException(f"工作空间成员 {member_id} 不存在于工作空间 {workspace_id}", BizCode.WORKSPACE_MEMBER_NOT_FOUND)
|
||||
|
||||
try:
|
||||
|
||||
try:
|
||||
workspace_member.is_active = False
|
||||
workspace_member.user.current_workspace_id = None
|
||||
db.commit()
|
||||
db.commit()
|
||||
business_logger.info(f"用户 {user.username} 成功删除工作空间 {workspace_id} 的成员 {member_id}")
|
||||
except Exception as e:
|
||||
db.rollback()
|
||||
business_logger.error(f"删除工作空间成员失败 - 工作空间: {workspace_id}, 成员: {member_id}, 错误: {str(e)}")
|
||||
business_logger.error(f"删除工作空间成员失败 - 工作空间: {workspace_id}, 成员: {member_id}, 错误: {str(e)}")
|
||||
raise BusinessException(f"删除工作空间成员失败: {str(e)}", BizCode.INTERNAL_ERROR)
|
||||
|
||||
|
||||
@@ -94,7 +91,7 @@ def _create_workspace_only(
|
||||
db: Session, workspace: WorkspaceCreate, owner: User
|
||||
) -> Workspace:
|
||||
business_logger.debug(f"创建工作空间: {workspace.name}, 创建者: {owner.username}")
|
||||
|
||||
|
||||
try:
|
||||
# Create the workspace without adding any members
|
||||
business_logger.debug(f"创建工作空间: {workspace.name}")
|
||||
@@ -126,7 +123,7 @@ def create_workspace(
|
||||
business_logger.info(f"工作空间创建成功: {db_workspace.name} (ID: {db_workspace.id}), 创建者: {user.username}")
|
||||
db.commit()
|
||||
db.refresh(db_workspace)
|
||||
|
||||
|
||||
# 如果 storage_type 是 "rag",自动创建知识库
|
||||
if workspace.storage_type == "rag":
|
||||
business_logger.info(
|
||||
@@ -138,7 +135,7 @@ def create_workspace(
|
||||
from app.schemas.knowledge_schema import KnowledgeCreate
|
||||
from app.models.knowledge_model import KnowledgeType, PermissionType
|
||||
from app.repositories import knowledge_repository
|
||||
|
||||
|
||||
# 创建知识库数据
|
||||
knowledge_data = KnowledgeCreate(
|
||||
workspace_id=db_workspace.id,
|
||||
@@ -162,10 +159,10 @@ def create_workspace(
|
||||
"html4excel": False
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
# 直接使用 repository 创建知识库,避免 service 层的额外逻辑
|
||||
db_knowledge = knowledge_repository.create_knowledge(
|
||||
db=db,
|
||||
db=db,
|
||||
knowledge=knowledge_data
|
||||
)
|
||||
db.commit()
|
||||
@@ -179,12 +176,12 @@ def create_workspace(
|
||||
)
|
||||
db.rollback()
|
||||
raise BusinessException(
|
||||
f"工作空间创建成功,但知识库创建失败: {str(kb_error)}",
|
||||
f"工作空间创建成功,但知识库创建失败: {str(kb_error)}",
|
||||
BizCode.INTERNAL_ERROR
|
||||
)
|
||||
|
||||
|
||||
return db_workspace
|
||||
|
||||
|
||||
except Exception as e:
|
||||
business_logger.error(f"工作空间创建失败: {workspace.name} - {str(e)}")
|
||||
db.rollback()
|
||||
@@ -195,7 +192,7 @@ def update_workspace(
|
||||
db: Session, workspace_id: uuid.UUID, workspace_in: WorkspaceUpdate, user: User
|
||||
) -> Workspace:
|
||||
business_logger.info(f"更新工作空间: workspace_id={workspace_id}, 操作者: {user.username}")
|
||||
|
||||
|
||||
db_workspace = _check_workspace_admin_permission(db,workspace_id,user)
|
||||
try:
|
||||
# 更新工作空间
|
||||
@@ -219,8 +216,8 @@ def get_workspace_members(
|
||||
db: Session, workspace_id: uuid.UUID, user: User
|
||||
) -> List[WorkspaceMember]:
|
||||
"""获取某工作空间的成员列表(关系序列化由模型关系支持)"""
|
||||
business_logger.info(f"获取工作空间成员: workspace_id={workspace_id}, 操作者: {user.username}")
|
||||
|
||||
business_logger.info(f"获取工作空间成员: workspace_id={workspace_id}, 操作者: {user.username}")
|
||||
|
||||
# 查找工作空间
|
||||
business_logger.debug(f"查找工作空间: {workspace_id}")
|
||||
workspace = workspace_repository.get_workspace_by_id(db=db, workspace_id=workspace_id)
|
||||
@@ -237,10 +234,10 @@ def get_workspace_members(
|
||||
db=db, user_id=user.id, workspace_id=workspace_id
|
||||
)
|
||||
workspace_memberships = {workspace_id} if member else set()
|
||||
|
||||
|
||||
subject = Subject.from_user(user, workspace_memberships=workspace_memberships)
|
||||
resource = Resource.from_workspace(workspace)
|
||||
|
||||
|
||||
try:
|
||||
permission_service.require_permission(
|
||||
subject,
|
||||
@@ -265,7 +262,7 @@ def get_workspace_members(
|
||||
|
||||
def _generate_invite_token() -> tuple[str, str]:
|
||||
"""生成邀请令牌和其哈希值
|
||||
|
||||
|
||||
Returns:
|
||||
tuple: (原始令牌, 令牌哈希)
|
||||
"""
|
||||
@@ -285,21 +282,21 @@ def _check_workspace_member_permission(db: Session, workspace_id: uuid.UUID, use
|
||||
message="Workspace not found",
|
||||
code=BizCode.WORKSPACE_NOT_FOUND
|
||||
)
|
||||
|
||||
|
||||
# 使用统一权限服务检查访问权限
|
||||
from app.core.permissions import permission_service, Subject, Resource, Action
|
||||
|
||||
|
||||
# 获取用户的工作空间成员关系
|
||||
member = workspace_repository.get_member_in_workspace(
|
||||
db=db, user_id=user.id, workspace_id=workspace_id
|
||||
)
|
||||
|
||||
|
||||
# 任何成员都有访问权限
|
||||
workspace_memberships = {workspace_id} if member else set()
|
||||
|
||||
|
||||
subject = Subject.from_user(user, workspace_memberships=workspace_memberships)
|
||||
resource = Resource.from_workspace(db_workspace)
|
||||
|
||||
|
||||
try:
|
||||
permission_service.require_permission(
|
||||
subject,
|
||||
@@ -323,21 +320,21 @@ def _check_workspace_admin_permission(db: Session, workspace_id: uuid.UUID, user
|
||||
message="Workspace not found",
|
||||
code=BizCode.WORKSPACE_NOT_FOUND
|
||||
)
|
||||
|
||||
|
||||
# 使用统一权限服务检查管理权限
|
||||
from app.core.permissions import permission_service, Subject, Resource, Action
|
||||
|
||||
|
||||
# 获取用户的工作空间成员关系
|
||||
member = workspace_repository.get_member_in_workspace(
|
||||
db=db, user_id=user.id, workspace_id=workspace_id
|
||||
)
|
||||
|
||||
|
||||
# 只有 manager 才有管理权限
|
||||
workspace_memberships = {workspace_id} if (member and member.role == WorkspaceRole.manager) else set()
|
||||
|
||||
|
||||
subject = Subject.from_user(user, workspace_memberships=workspace_memberships)
|
||||
resource = Resource.from_workspace(db_workspace)
|
||||
|
||||
|
||||
try:
|
||||
permission_service.require_permission(
|
||||
subject,
|
||||
@@ -353,14 +350,14 @@ def _check_workspace_admin_permission(db: Session, workspace_id: uuid.UUID, user
|
||||
|
||||
|
||||
def create_workspace_invite(
|
||||
db: Session,
|
||||
workspace_id: uuid.UUID,
|
||||
invite_data: WorkspaceInviteCreate,
|
||||
db: Session,
|
||||
workspace_id: uuid.UUID,
|
||||
invite_data: WorkspaceInviteCreate,
|
||||
user: User
|
||||
) -> WorkspaceInviteResponse:
|
||||
"""创建工作空间邀请"""
|
||||
business_logger.info(f"创建工作空间邀请: workspace_id={workspace_id}, email={invite_data.email}, 创建者: {user.username}")
|
||||
|
||||
|
||||
try:
|
||||
# 检查权限
|
||||
_check_workspace_admin_permission(db, workspace_id, user)
|
||||
@@ -368,7 +365,7 @@ def create_workspace_invite(
|
||||
# 检查被邀请用户是否已经在工作空间中
|
||||
from app.repositories import user_repository
|
||||
invited_user = user_repository.get_user_by_email(db, invite_data.email)
|
||||
|
||||
|
||||
if invited_user:
|
||||
# 用户存在,检查是否已经是工作空间成员
|
||||
existing_member = workspace_repository.get_member_in_workspace(
|
||||
@@ -379,14 +376,14 @@ def create_workspace_invite(
|
||||
if existing_member:
|
||||
business_logger.warning(f"用户 {invite_data.email} 已经是工作空间成员")
|
||||
raise BusinessException("该用户已经是工作空间成员", BizCode.RESOURCE_ALREADY_EXISTS)
|
||||
|
||||
|
||||
# 检查是否已有待处理的邀请
|
||||
invite_repo = WorkspaceInviteRepository(db)
|
||||
existing_invite = invite_repo.get_pending_invite_by_email_and_workspace(
|
||||
email=invite_data.email,
|
||||
email=invite_data.email,
|
||||
workspace_id=workspace_id
|
||||
)
|
||||
|
||||
|
||||
invite_token = None
|
||||
if existing_invite:
|
||||
business_logger.info(f"邮箱 {invite_data.email} 在工作空间 {workspace_id} 已有待处理邀请,返回现有邀请")
|
||||
@@ -409,17 +406,17 @@ def create_workspace_invite(
|
||||
)
|
||||
db.commit()
|
||||
db.refresh(db_invite)
|
||||
invite_token = token
|
||||
|
||||
invite_token = token
|
||||
|
||||
invite_obj = existing_invite or db_invite
|
||||
business_logger.info(f"工作空间邀请创建成功: invite_id={invite_obj.id}, email={invite_data.email}")
|
||||
|
||||
|
||||
# 构造响应
|
||||
response = WorkspaceInviteResponse.model_validate(invite_obj)
|
||||
response.invite_token = invite_token
|
||||
return response
|
||||
|
||||
|
||||
|
||||
|
||||
except Exception as e:
|
||||
db.rollback()
|
||||
business_logger.error(f"创建工作空间邀请失败: workspace_id={workspace_id}, email={invite_data.email} - {str(e)}")
|
||||
@@ -427,8 +424,8 @@ def create_workspace_invite(
|
||||
|
||||
|
||||
def get_workspace_invites(
|
||||
db: Session,
|
||||
workspace_id: uuid.UUID,
|
||||
db: Session,
|
||||
workspace_id: uuid.UUID,
|
||||
user: User,
|
||||
status: Optional[InviteStatus] = None,
|
||||
limit: int = 50,
|
||||
@@ -436,15 +433,15 @@ def get_workspace_invites(
|
||||
) -> List[WorkspaceInviteResponse]:
|
||||
"""获取工作空间邀请列表"""
|
||||
business_logger.info(f"获取工作空间邀请列表: workspace_id={workspace_id}, 操作者: {user.username}")
|
||||
|
||||
|
||||
# 检查工作空间是否存在
|
||||
workspace = workspace_repository.get_workspace_by_id(db=db, workspace_id=workspace_id)
|
||||
if not workspace:
|
||||
raise BusinessException("工作空间不存在", BizCode.WORKSPACE_NOT_FOUND)
|
||||
|
||||
|
||||
# 检查权限
|
||||
_check_workspace_admin_permission(db, workspace_id, user)
|
||||
|
||||
|
||||
# 获取邀请列表
|
||||
invite_repo = WorkspaceInviteRepository(db)
|
||||
invites = invite_repo.get_workspace_invites(
|
||||
@@ -453,35 +450,35 @@ def get_workspace_invites(
|
||||
limit=limit,
|
||||
offset=offset
|
||||
)
|
||||
|
||||
|
||||
return [WorkspaceInviteResponse.model_validate(invite) for invite in invites]
|
||||
|
||||
|
||||
def validate_invite_token(db: Session, token: str) -> InviteValidateResponse:
|
||||
"""验证邀请令牌"""
|
||||
business_logger.info("验证邀请令牌")
|
||||
|
||||
|
||||
# 生成令牌哈希
|
||||
token_hash = hashlib.sha256(token.encode()).hexdigest()
|
||||
|
||||
|
||||
# 查找邀请
|
||||
invite_repo = WorkspaceInviteRepository(db)
|
||||
invite = invite_repo.get_invite_by_token_hash(token_hash)
|
||||
|
||||
|
||||
if not invite:
|
||||
business_logger.warning("邀请令牌无效")
|
||||
raise BusinessException("邀请令牌无效", BizCode.WORKSPACE_INVITE_NOT_FOUND)
|
||||
|
||||
|
||||
# 检查邀请状态和过期时间
|
||||
now = datetime.datetime.now()
|
||||
is_expired = invite.expires_at < now or invite.status != InviteStatus.pending
|
||||
is_valid = not is_expired
|
||||
|
||||
|
||||
# 获取工作空间信息
|
||||
workspace = workspace_repository.get_workspace_by_id(db=db, workspace_id=invite.workspace_id)
|
||||
|
||||
|
||||
business_logger.info(f"邀请令牌验证完成: valid={is_valid}, expired={is_expired}")
|
||||
|
||||
|
||||
return InviteValidateResponse(
|
||||
workspace_name=workspace.name,
|
||||
workspace_id=invite.workspace_id,
|
||||
@@ -493,32 +490,32 @@ def validate_invite_token(db: Session, token: str) -> InviteValidateResponse:
|
||||
|
||||
|
||||
def accept_workspace_invite(
|
||||
db: Session,
|
||||
accept_request: InviteAcceptRequest,
|
||||
db: Session,
|
||||
accept_request: InviteAcceptRequest,
|
||||
user: User
|
||||
) -> dict:
|
||||
"""接受工作空间邀请"""
|
||||
business_logger.info(f"接受工作空间邀请: 用户 {user.username}")
|
||||
|
||||
|
||||
try:
|
||||
from app.core.config import settings
|
||||
|
||||
|
||||
# 生成令牌哈希
|
||||
token_hash = hashlib.sha256(accept_request.token.encode()).hexdigest()
|
||||
|
||||
|
||||
# 查找邀请
|
||||
invite_repo = WorkspaceInviteRepository(db)
|
||||
invite = invite_repo.get_invite_by_token_hash(token_hash)
|
||||
|
||||
|
||||
if not invite:
|
||||
business_logger.warning("邀请令牌无效")
|
||||
raise BusinessException("邀请令牌无效", BizCode.WORKSPACE_INVITE_NOT_FOUND)
|
||||
|
||||
|
||||
# 检查邀请状态
|
||||
if invite.status != InviteStatus.pending:
|
||||
business_logger.warning(f"邀请已被处理: status={invite.status}")
|
||||
raise BusinessException(f"邀请已被{invite.status}", BizCode.WORKSPACE_INVITE_INVALID)
|
||||
|
||||
|
||||
# 检查过期时间
|
||||
now = datetime.datetime.now()
|
||||
if invite.expires_at < now:
|
||||
@@ -526,31 +523,31 @@ def accept_workspace_invite(
|
||||
# 标记为过期
|
||||
invite_repo.update_invite_status(invite.id, InviteStatus.expired)
|
||||
raise BusinessException("邀请已过期", BizCode.WORKSPACE_INVITE_EXPIRED)
|
||||
|
||||
|
||||
# 检查邮箱是否匹配
|
||||
if invite.email != user.email:
|
||||
business_logger.warning(f"邮箱不匹配: invite_email={invite.email}, user_email={user.email}")
|
||||
raise BusinessException("邮箱与邀请邮箱不匹配", BizCode.FORBIDDEN)
|
||||
|
||||
|
||||
# 如果启用单工作空间模式,检查用户是否已有工作空间
|
||||
if settings.ENABLE_SINGLE_WORKSPACE:
|
||||
user_workspaces = workspace_repository.get_workspaces_by_user(db=db, user_id=user.id)
|
||||
if user_workspaces:
|
||||
business_logger.warning(f"单工作空间模式下用户已有工作空间: user={user.username}")
|
||||
raise BusinessException("用户只能加入一个工作空间", BizCode.FORBIDDEN)
|
||||
|
||||
|
||||
# 检查用户是否已经是工作空间成员
|
||||
existing_member = workspace_repository.get_member_in_workspace(
|
||||
db=db,
|
||||
user_id=user.id,
|
||||
db=db,
|
||||
user_id=user.id,
|
||||
workspace_id=invite.workspace_id
|
||||
)
|
||||
|
||||
|
||||
if existing_member:
|
||||
business_logger.info("用户已是工作空间成员,更新邀请状态")
|
||||
invite_repo.update_invite_status(
|
||||
invite.id,
|
||||
InviteStatus.accepted,
|
||||
invite.id,
|
||||
InviteStatus.accepted,
|
||||
accepted_at=now
|
||||
)
|
||||
db.commit()
|
||||
@@ -559,10 +556,10 @@ def accept_workspace_invite(
|
||||
"message": "You are already a member of this workspace",
|
||||
"workspace": workspace
|
||||
}
|
||||
|
||||
|
||||
# 将角色映射到工作空间角色(现在直接使用相同的角色)
|
||||
workspace_role = invite.role
|
||||
|
||||
|
||||
# 添加用户到工作空间
|
||||
workspace_repository.add_member_to_workspace(
|
||||
db=db,
|
||||
@@ -570,27 +567,27 @@ def accept_workspace_invite(
|
||||
workspace_id=invite.workspace_id,
|
||||
role=workspace_role
|
||||
)
|
||||
|
||||
|
||||
# 标记邀请为已接受
|
||||
invite_repo.update_invite_status(
|
||||
invite.id,
|
||||
InviteStatus.accepted,
|
||||
invite.id,
|
||||
InviteStatus.accepted,
|
||||
accepted_at=now
|
||||
)
|
||||
|
||||
|
||||
db.commit()
|
||||
|
||||
|
||||
# 获取工作空间信息
|
||||
workspace = workspace_repository.get_workspace_by_id(db=db, workspace_id=invite.workspace_id)
|
||||
|
||||
|
||||
business_logger.info(f"用户成功加入工作空间: user={user.username}, workspace={workspace.name}, role={workspace_role}")
|
||||
|
||||
|
||||
return {
|
||||
"message": "Successfully joined the workspace",
|
||||
"workspace": workspace,
|
||||
"role": workspace_role
|
||||
}
|
||||
|
||||
|
||||
except Exception as e:
|
||||
db.rollback()
|
||||
business_logger.error(f"接受工作空间邀请失败: user={user.username} - {str(e)}")
|
||||
@@ -598,34 +595,34 @@ def accept_workspace_invite(
|
||||
|
||||
|
||||
def revoke_workspace_invite(
|
||||
db: Session,
|
||||
workspace_id: uuid.UUID,
|
||||
invite_id: uuid.UUID,
|
||||
db: Session,
|
||||
workspace_id: uuid.UUID,
|
||||
invite_id: uuid.UUID,
|
||||
user: User
|
||||
) -> dict:
|
||||
"""撤销工作空间邀请"""
|
||||
business_logger.info(f"撤销工作空间邀请: workspace_id={workspace_id}, invite_id={invite_id}, 操作者: {user.username}")
|
||||
|
||||
|
||||
try:
|
||||
# 检查权限
|
||||
_check_workspace_admin_permission(db, workspace_id, user)
|
||||
|
||||
|
||||
# 撤销邀请
|
||||
invite_repo = WorkspaceInviteRepository(db)
|
||||
invite = invite_repo.revoke_invite(invite_id)
|
||||
|
||||
|
||||
if not invite:
|
||||
business_logger.warning(f"邀请不存在: invite_id={invite_id}")
|
||||
raise BusinessException("邀请不存在", BizCode.WORKSPACE_INVITE_NOT_FOUND)
|
||||
|
||||
|
||||
if invite.workspace_id != workspace_id:
|
||||
business_logger.warning(f"邀请不属于指定工作空间: invite_id={invite_id}, workspace_id={workspace_id}")
|
||||
raise BusinessException("邀请不属于指定工作空间", BizCode.BAD_REQUEST)
|
||||
|
||||
|
||||
db.commit()
|
||||
business_logger.info(f"工作空间邀请撤销成功: invite_id={invite_id}")
|
||||
return {"message": "邀请撤销成功"}
|
||||
|
||||
|
||||
except Exception as e:
|
||||
db.rollback()
|
||||
business_logger.error(f"撤销工作空间邀请失败: invite_id={invite_id} - {str(e)}")
|
||||
@@ -640,48 +637,48 @@ def update_workspace_member_roles(
|
||||
) -> List[WorkspaceMember]:
|
||||
"""更新工作空间成员角色"""
|
||||
business_logger.info(f"更新工作空间成员角色: workspace_id={workspace_id}, 操作者: {user.username}, 更新数量: {len(updates)}")
|
||||
|
||||
|
||||
# 检查管理员权限
|
||||
_check_workspace_admin_permission(db, workspace_id, user)
|
||||
|
||||
|
||||
# 获取所有当前成员
|
||||
all_members = workspace_repository.get_members_by_workspace(db=db, workspace_id=workspace_id)
|
||||
member_map = {m.id: m for m in all_members}
|
||||
|
||||
|
||||
# 验证和业务规则检查
|
||||
update_ids = set()
|
||||
for upd in updates:
|
||||
# 检查成员是否存在
|
||||
if upd.id not in member_map:
|
||||
raise BusinessException(f"成员 {upd.id} 不存在于工作空间 {workspace_id}", BizCode.WORKSPACE_MEMBER_NOT_FOUND)
|
||||
|
||||
|
||||
member = member_map[upd.id]
|
||||
|
||||
|
||||
# 检查成员是否属于该工作空间
|
||||
if member.workspace_id != workspace_id:
|
||||
raise BusinessException(f"成员 {upd.id} 不属于工作空间 {workspace_id}", BizCode.WORKSPACE_MEMBER_NOT_FOUND)
|
||||
|
||||
|
||||
# 不能修改自己的角色
|
||||
if member.user_id == user.id:
|
||||
raise BusinessException("不能修改自己的角色", BizCode.BAD_REQUEST)
|
||||
|
||||
|
||||
update_ids.add(upd.id)
|
||||
|
||||
|
||||
# 检查是否至少保留一个 manager
|
||||
current_managers = [m for m in all_members if m.role == WorkspaceRole.manager]
|
||||
managers_after_update = [
|
||||
m for m in all_members
|
||||
m for m in all_members
|
||||
if m.id not in update_ids and m.role == WorkspaceRole.manager
|
||||
]
|
||||
|
||||
|
||||
# 添加更新后会成为 manager 的成员
|
||||
for upd in updates:
|
||||
if upd.role == WorkspaceRole.manager:
|
||||
managers_after_update.append(member_map[upd.id])
|
||||
|
||||
|
||||
if len(managers_after_update) == 0:
|
||||
raise BusinessException("工作空间至少需要一个管理员", BizCode.BAD_REQUEST)
|
||||
|
||||
|
||||
# 执行更新
|
||||
try:
|
||||
for upd in updates:
|
||||
@@ -691,15 +688,15 @@ def update_workspace_member_roles(
|
||||
role=upd.role,
|
||||
)
|
||||
business_logger.debug(f"更新成员 {upd.id} 角色为 {upd.role}")
|
||||
|
||||
|
||||
db.commit()
|
||||
|
||||
|
||||
# 重新获取更新后的成员列表
|
||||
updated_members = workspace_repository.get_members_by_workspace(db=db, workspace_id=workspace_id)
|
||||
business_logger.info(f"成员角色更新完成: workspace_id={workspace_id}, 更新数量={len(updates)}")
|
||||
|
||||
|
||||
return updated_members
|
||||
|
||||
|
||||
except Exception as e:
|
||||
db.rollback()
|
||||
business_logger.error(f"更新工作空间成员角色失败: workspace_id={workspace_id} - {str(e)}")
|
||||
@@ -789,7 +786,7 @@ def get_workspace_models_configs(
|
||||
|
||||
# 查询工作空间模型配置
|
||||
configs = workspace_repository.get_workspace_models_configs(db=db, workspace_id=workspace_id)
|
||||
|
||||
|
||||
if configs is None:
|
||||
business_logger.error(f"工作空间不存在: workspace_id={workspace_id}")
|
||||
raise BusinessException(
|
||||
@@ -801,4 +798,5 @@ def get_workspace_models_configs(
|
||||
f"成功获取工作空间 {workspace_id} 的模型配置: "
|
||||
f"llm={configs.get('llm')}, embedding={configs.get('embedding')}, rerank={configs.get('rerank')}"
|
||||
)
|
||||
return configs
|
||||
return configs
|
||||
|
||||
|
||||
Reference in New Issue
Block a user