# ============================================================================= # 企微IT智能服务台 — 管理员用户管理 API # ============================================================================= # 说明:管理员用户的 CRUD API # 端点: # GET /api/admin/users — 获取管理员列表 # POST /api/admin/users — 创建管理员 # GET /api/admin/users/{id} — 获取管理员详情 # PUT /api/admin/users/{id} — 更新管理员 # DELETE /api/admin/users/{id} — 删除管理员 # POST /api/admin/users/{id}/reset-password — 重置密码 # ============================================================================= import logging from typing import Optional from fastapi import APIRouter, Depends, Query from sqlalchemy.ext.asyncio import AsyncSession from app.database import get_db from app.dependencies import UserInfo, get_current_user, require_role from app.schemas.admin_user import ( AdminUserCreateRequest, AdminUserListResponse, AdminUserResetPasswordRequest, AdminUserResponse, AdminUserUpdateRequest, ) from app.services.admin_user_service import AdminUserService from app.utils.response import AppException, success_response from app.utils.error_codes import ErrorCode logger = logging.getLogger(__name__) # 创建路由器 router = APIRouter(prefix="/admin/users", tags=["管理员用户管理"]) # ============================================================================= # 0. GET /api/admin/users/me — 获取当前登录用户信息 # ============================================================================= @router.get("/me", response_model=None) async def get_current_admin_user( current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """获取当前登录的管理员用户信息。 无需额外权限,任何已登录用户都可以访问。 Args: current_user: 当前用户 db: 数据库会话 Returns: 当前用户信息 """ service = AdminUserService(db) agent = await service.get_user_by_user_id(current_user.employee_id) if not agent: raise AppException(ErrorCode.NOT_FOUND, "用户不存在") return success_response(data=AdminUserResponse( id=agent.id, user_id=agent.user_id, name=agent.name, role=agent.role, is_active=agent.status == "online", mfa_enabled=agent.mfa_enabled, mfa_bound_at=agent.mfa_bound_at, created_at=agent.created_at, updated_at=agent.updated_at, ).model_dump()) # ============================================================================= # 1. GET /api/admin/users — 获取管理员列表 # ============================================================================= @router.get("", response_model=None) @require_role("admin") async def list_admin_users( page: int = Query(1, ge=1, description="页码"), page_size: int = Query(20, ge=1, le=100, description="每页数量"), is_active: Optional[bool] = Query(None, description="是否激活(true=在线,false=离线)"), current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """获取管理员用户列表。 需要 admin 或 super_admin 角色。 Args: page: 页码 page_size: 每页数量 is_active: 按激活状态过滤 current_user: 当前用户 db: 数据库会话 Returns: 管理员列表 """ service = AdminUserService(db) items, total = await service.list_admin_users( page=page, page_size=page_size, is_active=is_active, ) # 转换为响应格式 user_responses = [] for agent in items: user_responses.append(AdminUserResponse( id=agent.id, user_id=agent.user_id, name=agent.name, role=agent.role, is_active=agent.status == "online", mfa_enabled=agent.mfa_enabled, mfa_bound_at=agent.mfa_bound_at, created_at=agent.created_at, updated_at=agent.updated_at, )) return success_response(data=AdminUserListResponse( items=user_responses, total=total, ).model_dump()) # ============================================================================= # 2. POST /api/admin/users — 创建管理员 # ============================================================================= @router.post("", response_model=None) @require_role("super_admin") async def create_admin_user( body: AdminUserCreateRequest, current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """创建管理员用户。 需要 super_admin 角色。 Args: body: 创建请求 current_user: 当前用户 db: 数据库会话 Returns: 创建的用户信息 """ service = AdminUserService(db) try: agent = await service.create_admin_user( user_id=body.user_id, name=body.name, role=body.role, password=body.password, ) await db.commit() return success_response(data=AdminUserResponse( id=agent.id, user_id=agent.user_id, name=agent.name, role=agent.role, is_active=agent.status == "online", mfa_enabled=agent.mfa_enabled, mfa_bound_at=agent.mfa_bound_at, created_at=agent.created_at, updated_at=agent.updated_at, ).model_dump()) except AppException: await db.rollback() raise except Exception as e: await db.rollback() logger.error(f"创建管理员失败: {e}") raise AppException(ErrorCode.INTERNAL_ERROR, "创建管理员失败") # ============================================================================= # 3. GET /api/admin/users/{id} — 获取管理员详情 # ============================================================================= @router.get("/{id}", response_model=None) @require_role("admin") async def get_admin_user( id: str, current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """获取管理员用户详情。 需要 admin 或 super_admin 角色。 Args: id: 用户ID current_user: 当前用户 db: 数据库会话 Returns: 用户详情 """ service = AdminUserService(db) agent = await service.get_user_by_id(id) if not agent: raise AppException(ErrorCode.NOT_FOUND, "用户不存在") return success_response(data=AdminUserResponse( id=agent.id, user_id=agent.user_id, name=agent.name, role=agent.role, is_active=agent.status == "online", mfa_enabled=agent.mfa_enabled, mfa_bound_at=agent.mfa_bound_at, created_at=agent.created_at, updated_at=agent.updated_at, ).model_dump()) # ============================================================================= # 4. PUT /api/admin/users/{id} — 更新管理员 # ============================================================================= @router.put("/{id}", response_model=None) @require_role("admin") async def update_admin_user( id: str, body: AdminUserUpdateRequest, current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """更新管理员用户。 需要 admin 或 super_admin 角色。 - admin 角色只能更新普通 admin - super_admin 角色可以更新所有用户 Args: id: 用户ID body: 更新请求 current_user: 当前用户 db: 数据库会话 Returns: 更新后的用户信息 """ # 权限检查:非 super_admin 不能修改 super_admin if "super_admin" not in current_user.roles: target = await AdminUserService(db).get_user_by_id(id) if target and target.role == "super_admin": raise AppException(ErrorCode.FORBIDDEN, "无法修改超级管理员") service = AdminUserService(db) try: agent = await service.update_admin_user( id=id, name=body.name, role=body.role, is_active=body.is_active, ) await db.commit() return success_response(data=AdminUserResponse( id=agent.id, user_id=agent.user_id, name=agent.name, role=agent.role, is_active=agent.status == "online", mfa_enabled=agent.mfa_enabled, mfa_bound_at=agent.mfa_bound_at, created_at=agent.created_at, updated_at=agent.updated_at, ).model_dump()) except AppException: await db.rollback() raise except Exception as e: await db.rollback() logger.error(f"更新管理员失败: {e}") raise AppException(ErrorCode.INTERNAL_ERROR, "更新管理员失败") # ============================================================================= # 5. DELETE /api/admin/users/{id} — 删除管理员 # ============================================================================= @router.delete("/{id}", response_model=None) @require_role("super_admin") async def delete_admin_user( id: str, current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """删除管理员用户。 需要 super_admin 角色。 Args: id: 用户ID current_user: 当前用户 db: 数据库会话 Returns: 删除结果 """ service = AdminUserService(db) try: await service.delete_admin_user(id) await db.commit() return success_response(data={"message": "删除成功"}) except AppException: await db.rollback() raise except Exception as e: await db.rollback() logger.error(f"删除管理员失败: {e}") raise AppException(ErrorCode.INTERNAL_ERROR, "删除管理员失败") # ============================================================================= # 6. POST /api/admin/users/{id}/reset-password — 重置密码 # ============================================================================= @router.post("/{id}/reset-password", response_model=None) @require_role("admin") async def reset_password( id: str, body: AdminUserResetPasswordRequest, current_user: UserInfo = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): """重置管理员密码。 需要 admin 或 super_admin 角色。 Args: id: 用户ID body: 重置请求 current_user: 当前用户 db: 数据库会话 Returns: 重置结果 """ # 权限检查:非 super_admin 不能重置 super_admin 的密码 if "super_admin" not in current_user.roles: target = await AdminUserService(db).get_user_by_id(id) if target and target.role == "super_admin": raise AppException(ErrorCode.FORBIDDEN, "无法重置超级管理员密码") service = AdminUserService(db) try: await service.reset_password(id, body.new_password) await db.commit() return success_response(data={"message": "密码重置成功"}) except AppException: await db.rollback() raise except Exception as e: await db.rollback() logger.error(f"重置密码失败: {e}") raise AppException(ErrorCode.INTERNAL_ERROR, "重置密码失败")