Introduced groups and added all related endpoints
All checks were successful
AWS Deploy on Push / build (push) Successful in 7m39s
All checks were successful
AWS Deploy on Push / build (push) Successful in 7m39s
This commit is contained in:
169
app/routers/groups.py
Normal file
169
app/routers/groups.py
Normal file
@@ -0,0 +1,169 @@
|
||||
from uuid import UUID
|
||||
|
||||
from fastapi import APIRouter, Depends, HTTPException, status
|
||||
from sqlalchemy.orm import Session
|
||||
|
||||
from app.auth.dependencies import get_current_user, require_roles
|
||||
from app.models import Group
|
||||
from app.models.auth import CognitoUser
|
||||
from app.models.schemas import (
|
||||
GroupBulkSort,
|
||||
GroupCreate,
|
||||
GroupResponse,
|
||||
GroupSortUpdate,
|
||||
GroupUpdate,
|
||||
)
|
||||
from app.utils.database import get_db
|
||||
|
||||
router = APIRouter(prefix="/groups", tags=["groups"])
|
||||
|
||||
|
||||
@router.post("/", response_model=GroupResponse, status_code=status.HTTP_201_CREATED)
|
||||
@require_roles("admin")
|
||||
def create_group(
|
||||
group: GroupCreate,
|
||||
db: Session = Depends(get_db),
|
||||
user: CognitoUser = Depends(get_current_user),
|
||||
):
|
||||
"""Create a new channel group"""
|
||||
# Check for duplicate group name
|
||||
existing_group = db.query(Group).filter(Group.name == group.name).first()
|
||||
if existing_group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_409_CONFLICT,
|
||||
detail="Group with this name already exists",
|
||||
)
|
||||
|
||||
db_group = Group(**group.model_dump())
|
||||
db.add(db_group)
|
||||
db.commit()
|
||||
db.refresh(db_group)
|
||||
return db_group
|
||||
|
||||
|
||||
@router.get("/{group_id}", response_model=GroupResponse)
|
||||
def get_group(group_id: UUID, db: Session = Depends(get_db)):
|
||||
"""Get a group by id"""
|
||||
group = db.query(Group).filter(Group.id == group_id).first()
|
||||
if not group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_404_NOT_FOUND, detail="Group not found"
|
||||
)
|
||||
return group
|
||||
|
||||
|
||||
@router.put("/{group_id}", response_model=GroupResponse)
|
||||
@require_roles("admin")
|
||||
def update_group(
|
||||
group_id: UUID,
|
||||
group: GroupUpdate,
|
||||
db: Session = Depends(get_db),
|
||||
user: CognitoUser = Depends(get_current_user),
|
||||
):
|
||||
"""Update a group's name or sort order"""
|
||||
db_group = db.query(Group).filter(Group.id == group_id).first()
|
||||
if not db_group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_404_NOT_FOUND, detail="Group not found"
|
||||
)
|
||||
|
||||
# Check for duplicate name if name is being updated
|
||||
if group.name is not None and group.name != db_group.name:
|
||||
existing_group = db.query(Group).filter(Group.name == group.name).first()
|
||||
if existing_group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_409_CONFLICT,
|
||||
detail="Group with this name already exists",
|
||||
)
|
||||
|
||||
# Update only provided fields
|
||||
update_data = group.model_dump(exclude_unset=True)
|
||||
for key, value in update_data.items():
|
||||
setattr(db_group, key, value)
|
||||
|
||||
db.commit()
|
||||
db.refresh(db_group)
|
||||
return db_group
|
||||
|
||||
|
||||
@router.delete("/{group_id}", status_code=status.HTTP_204_NO_CONTENT)
|
||||
@require_roles("admin")
|
||||
def delete_group(
|
||||
group_id: UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: CognitoUser = Depends(get_current_user),
|
||||
):
|
||||
"""Delete a group (only if it has no channels)"""
|
||||
group = db.query(Group).filter(Group.id == group_id).first()
|
||||
if not group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_404_NOT_FOUND, detail="Group not found"
|
||||
)
|
||||
|
||||
# Check if group has any channels
|
||||
if group.channels:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_400_BAD_REQUEST,
|
||||
detail="Cannot delete group with existing channels",
|
||||
)
|
||||
|
||||
db.delete(group)
|
||||
db.commit()
|
||||
return None
|
||||
|
||||
|
||||
@router.get("/", response_model=list[GroupResponse])
|
||||
def list_groups(db: Session = Depends(get_db)):
|
||||
"""List all groups sorted by sort_order"""
|
||||
return db.query(Group).order_by(Group.sort_order).all()
|
||||
|
||||
|
||||
@router.put("/{group_id}/sort", response_model=GroupResponse)
|
||||
@require_roles("admin")
|
||||
def update_group_sort_order(
|
||||
group_id: UUID,
|
||||
sort_update: GroupSortUpdate,
|
||||
db: Session = Depends(get_db),
|
||||
user: CognitoUser = Depends(get_current_user),
|
||||
):
|
||||
"""Update a single group's sort order"""
|
||||
db_group = db.query(Group).filter(Group.id == group_id).first()
|
||||
if not db_group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_404_NOT_FOUND, detail="Group not found"
|
||||
)
|
||||
|
||||
db_group.sort_order = sort_update.sort_order
|
||||
db.commit()
|
||||
db.refresh(db_group)
|
||||
return db_group
|
||||
|
||||
|
||||
@router.post("/reorder", response_model=list[GroupResponse])
|
||||
@require_roles("admin")
|
||||
def bulk_update_sort_orders(
|
||||
bulk_sort: GroupBulkSort,
|
||||
db: Session = Depends(get_db),
|
||||
user: CognitoUser = Depends(get_current_user),
|
||||
):
|
||||
"""Bulk update group sort orders"""
|
||||
groups_to_update = []
|
||||
|
||||
for group_data in bulk_sort.groups:
|
||||
group_id = group_data["group_id"]
|
||||
sort_order = group_data["sort_order"]
|
||||
|
||||
group = db.query(Group).filter(Group.id == str(group_id)).first()
|
||||
if not group:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_404_NOT_FOUND,
|
||||
detail=f"Group with id {group_id} not found",
|
||||
)
|
||||
|
||||
group.sort_order = sort_order
|
||||
groups_to_update.append(group)
|
||||
|
||||
db.commit()
|
||||
|
||||
# Return all groups in their new order
|
||||
return db.query(Group).order_by(Group.sort_order).all()
|
||||
Reference in New Issue
Block a user