| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146 |
- import logging
- from typing import List, Any, Dict
- from fastapi import APIRouter, Depends, HTTPException, Request
- from sqlalchemy.orm import Session
- from sqlalchemy.exc import IntegrityError
- from app.api.v1 import deps
- from app.core.utils import get_client_ip
- from app.models.user import User
- from app.models.organization import Organization
- from app.schemas.organization import (
- OrganizationCreate,
- OrganizationUpdate,
- OrganizationResponse,
- )
- from app.services.captcha_service import CaptchaService
- from app.services.log_service import LogService
- from app.schemas.operation_log import ActionType
- router = APIRouter()
- logger = logging.getLogger(__name__)
- @router.get("/", response_model=List[OrganizationResponse], summary="组织列表")
- def list_organizations(
- db: Session = Depends(deps.get_db),
- current_user: User = Depends(deps.get_current_active_user),
- ):
- """扁平组织列表(登录用户可拉取下拉选项)。"""
- return (
- db.query(Organization)
- .order_by(Organization.sort_order.asc(), Organization.id.asc())
- .all()
- )
- @router.post("/", response_model=OrganizationResponse, summary="创建组织")
- def create_organization(
- body: OrganizationCreate,
- request: Request,
- db: Session = Depends(deps.get_db),
- current_user: User = Depends(deps.get_current_active_user),
- ):
- if current_user.role != "SUPER_ADMIN":
- raise HTTPException(status_code=403, detail="权限不足")
- org = Organization(
- name=body.name.strip(),
- description=body.description,
- sort_order=body.sort_order,
- )
- db.add(org)
- try:
- db.commit()
- db.refresh(org)
- except IntegrityError:
- db.rollback()
- raise HTTPException(status_code=400, detail="组织名称已存在")
- LogService.create_log(
- db=db,
- operator_id=current_user.id,
- action_type=ActionType.ORG_CREATE,
- target_user_id=None,
- target_mobile=None,
- ip_address=get_client_ip(request),
- details={
- "resource": "organization",
- "organization_id": org.id,
- "name": org.name,
- "description": org.description,
- "sort_order": org.sort_order,
- },
- )
- logger.info(f"创建组织: {org.name} (Operator: {current_user.mobile})")
- return org
- @router.put("/{organization_id}", response_model=OrganizationResponse, summary="更新组织")
- def update_organization(
- organization_id: int,
- body: OrganizationUpdate,
- request: Request,
- db: Session = Depends(deps.get_db),
- current_user: User = Depends(deps.get_current_active_user),
- ):
- if current_user.role != "SUPER_ADMIN":
- raise HTTPException(status_code=403, detail="权限不足")
- if not CaptchaService.verify_captcha(body.captcha_id, body.captcha_code):
- logger.warning(f"更新组织失败: 验证码错误 (User: {current_user.mobile})")
- raise HTTPException(status_code=400, detail="验证码错误或已过期")
- org = db.query(Organization).filter(Organization.id == organization_id).first()
- if not org:
- raise HTTPException(status_code=404, detail="组织不存在")
- raw = body.model_dump(exclude_unset=True, exclude={"captcha_id", "captcha_code"})
- if not raw:
- raise HTTPException(status_code=400, detail="请至少修改一项内容")
- changes: Dict[str, Any] = {}
- if "name" in raw and raw["name"] is not None:
- new_name = raw["name"].strip()
- if new_name != org.name:
- changes["name"] = {"old": org.name, "new": new_name}
- if "description" in raw:
- if raw["description"] != org.description:
- changes["description"] = {"old": org.description, "new": raw["description"]}
- if "sort_order" in raw and raw["sort_order"] is not None:
- if raw["sort_order"] != org.sort_order:
- changes["sort_order"] = {"old": org.sort_order, "new": raw["sort_order"]}
- if not changes:
- raise HTTPException(status_code=400, detail="未检测到变更")
- if "name" in raw and raw["name"] is not None:
- org.name = raw["name"].strip()
- if "description" in raw:
- org.description = raw["description"]
- if "sort_order" in raw and raw["sort_order"] is not None:
- org.sort_order = raw["sort_order"]
- try:
- db.commit()
- db.refresh(org)
- except IntegrityError:
- db.rollback()
- raise HTTPException(status_code=400, detail="组织名称已存在")
- LogService.create_log(
- db=db,
- operator_id=current_user.id,
- action_type=ActionType.ORG_UPDATE,
- target_user_id=None,
- target_mobile=None,
- ip_address=get_client_ip(request),
- details={
- "resource": "organization",
- "organization_id": org.id,
- "changes": changes,
- },
- )
- logger.info(f"更新组织: {org.name} (Operator: {current_user.mobile})")
- return org
|