Files
ctms/backend/app/api/v1/permission_templates.py
T
2026-05-29 10:20:42 +08:00

127 lines
4.5 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
"""权限模板管理API"""
from __future__ import annotations
import uuid
from typing import Annotated, Optional
from fastapi import APIRouter, Depends, HTTPException, status
from fastapi.responses import Response
from sqlalchemy.ext.asyncio import AsyncSession
from app.core.deps import get_current_user, get_db_session, require_roles, require_study_roles
from app.models.permission_template import TemplateType
from app.schemas.permission_template import (
ApplyTemplateRequest,
ApplyTemplateResponse,
PermissionTemplateCreate,
PermissionTemplateRead,
PermissionTemplateUpdate,
)
from app.services.permission_template_service import PermissionTemplateService
# 模板管理路由(不需要 study_id)
router = APIRouter(prefix="/permission-templates", tags=["permission-templates"])
# 项目级模板操作路由(需要 study_id,挂载到 /studies/{study_id}
study_router = APIRouter(prefix="/permission-templates", tags=["permission-templates"])
@router.get("", response_model=list[PermissionTemplateRead])
async def list_templates(
template_type: Optional[str] = None,
category: Optional[str] = None,
skip: int = 0,
limit: int = 100,
db: Annotated[AsyncSession, Depends(get_db_session)] = None,
) -> list[PermissionTemplateRead]:
"""列表权限模板"""
t_type = TemplateType(template_type) if template_type else None
templates = await PermissionTemplateService.list_templates(
db, template_type=t_type, category=category, skip=skip, limit=limit
)
return [PermissionTemplateRead.model_validate(t) for t in templates]
@router.post(
"",
response_model=PermissionTemplateRead,
status_code=status.HTTP_201_CREATED,
)
async def create_template(
payload: PermissionTemplateCreate,
db: Annotated[AsyncSession, Depends(get_db_session)] = None,
current_user=Depends(require_roles(["ADMIN"])),
) -> PermissionTemplateRead:
"""创建权限模板"""
try:
template = await PermissionTemplateService.create_template(db, payload, current_user.id)
return PermissionTemplateRead.model_validate(template)
except ValueError as e:
raise HTTPException(status_code=status.HTTP_400_BAD_REQUEST, detail=str(e))
@router.get("/{template_id}", response_model=PermissionTemplateRead)
async def get_template(
template_id: uuid.UUID,
db: Annotated[AsyncSession, Depends(get_db_session)] = None,
) -> PermissionTemplateRead:
"""获取权限模板"""
template = await PermissionTemplateService.get_template(db, template_id)
if not template:
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="模板不存在")
return PermissionTemplateRead.model_validate(template)
@router.put("/{template_id}", response_model=PermissionTemplateRead)
async def update_template(
template_id: uuid.UUID,
payload: PermissionTemplateUpdate,
db: Annotated[AsyncSession, Depends(get_db_session)] = None,
current_user=Depends(require_roles(["ADMIN"])),
) -> PermissionTemplateRead:
"""更新权限模板"""
try:
template = await PermissionTemplateService.update_template(db, template_id, payload)
return PermissionTemplateRead.model_validate(template)
except ValueError as e:
raise HTTPException(status_code=status.HTTP_400_BAD_REQUEST, detail=str(e))
@router.delete("/{template_id}", status_code=status.HTTP_204_NO_CONTENT, response_class=Response)
async def delete_template(
template_id: uuid.UUID,
db: Annotated[AsyncSession, Depends(get_db_session)] = None,
current_user=Depends(require_roles(["ADMIN"])),
):
"""删除权限模板"""
try:
await PermissionTemplateService.delete_template(db, template_id)
except ValueError as e:
raise HTTPException(status_code=status.HTTP_400_BAD_REQUEST, detail=str(e))
@study_router.post(
"/{template_id}/apply",
response_model=ApplyTemplateResponse,
)
async def apply_template(
study_id: uuid.UUID,
template_id: uuid.UUID,
payload: ApplyTemplateRequest,
db: Annotated[AsyncSession, Depends(get_db_session)] = None,
_=Depends(require_study_roles(["PM"])),
) -> ApplyTemplateResponse:
"""应用权限模板到项目"""
try:
result = await PermissionTemplateService.apply_template(
db,
study_id,
payload.template_id,
roles=payload.roles,
override=payload.override,
)
return ApplyTemplateResponse(**result)
except ValueError as e:
raise HTTPException(status_code=status.HTTP_400_BAD_REQUEST, detail=str(e))