import logging from fastapi import APIRouter, Depends, HTTPException, Request from bson import ObjectId from src.dependencies import TeamServiceDep from src.schemas.team import TeamCreate, TeamUpdate, TeamResponse, TeamListResponse from src.utils.logging import log_request logger = logging.getLogger(__name__) router = APIRouter(tags=["Teams"], prefix="/teams") @router.post("", response_model=TeamResponse, status_code=201) async def create_team( team_data: TeamCreate, request: Request, team_service: TeamServiceDep = Depends() ): """ Create a new team Creates a new team with the provided information. Teams are used to organize users and control access to resources. Args: team_data: Team creation data including name and description team_service: Injected team service Returns: TeamResponse: The created team information Raises: 400: Invalid input data or team already exists 500: Internal server error """ log_request( {"path": request.url.path, "method": request.method, "team_data": team_data.dict()} ) try: response = await team_service.create_team(team_data) logger.info(f"Created new team: {team_data.name}") return response except ValueError as e: logger.warning(f"Invalid input for team creation: {e}") raise HTTPException(status_code=400, detail=str(e)) except Exception as e: logger.error(f"Unexpected error creating team: {e}") raise HTTPException(status_code=500, detail="Internal server error") @router.get("", response_model=TeamListResponse) async def list_teams( request: Request, team_service: TeamServiceDep = Depends() ): """ List all teams Retrieves a complete list of all teams in the system with their basic information and member counts. Args: team_service: Injected team service Returns: TeamListResponse: List of all teams with total count Raises: 500: Internal server error """ log_request( {"path": request.url.path, "method": request.method} ) try: response = await team_service.list_teams() logger.info(f"Listed {response.total} teams") return response except Exception as e: logger.error(f"Unexpected error listing teams: {e}") raise HTTPException(status_code=500, detail="Internal server error") @router.get("/{team_id}", response_model=TeamResponse) async def get_team( team_id: str, request: Request, team_service: TeamServiceDep = Depends() ): """ Get a team by ID Retrieves detailed information for a specific team including member count and team settings. Args: team_id: The team ID to retrieve team_service: Injected team service Returns: TeamResponse: Complete team information Raises: 400: Invalid team ID format 404: Team not found 500: Internal server error """ log_request( {"path": request.url.path, "method": request.method, "team_id": team_id} ) try: response = await team_service.get_team(team_id) logger.info(f"Retrieved team {team_id}") return response except ValueError as e: logger.warning(f"Invalid team ID: {e}") raise HTTPException(status_code=400, detail=str(e)) except RuntimeError as e: logger.warning(f"Team not found: {e}") raise HTTPException(status_code=404, detail=str(e)) except Exception as e: logger.error(f"Unexpected error getting team: {e}") raise HTTPException(status_code=500, detail="Internal server error") @router.put("/{team_id}", response_model=TeamResponse) async def update_team( team_id: str, team_data: TeamUpdate, request: Request, team_service: TeamServiceDep = Depends() ): """ Update a team Updates the specified team's information. Only the provided fields will be updated, others remain unchanged. Args: team_id: The team ID to update team_data: The team update data team_service: Injected team service Returns: TeamResponse: Updated team information Raises: 400: Invalid team ID format or validation errors 404: Team not found 500: Internal server error """ log_request( {"path": request.url.path, "method": request.method, "team_id": team_id, "team_data": team_data.dict()} ) try: response = await team_service.update_team(team_id, team_data) logger.info(f"Updated team {team_id}") return response except ValueError as e: logger.warning(f"Invalid input for team update: {e}") raise HTTPException(status_code=400, detail=str(e)) except RuntimeError as e: logger.warning(f"Team not found for update: {e}") raise HTTPException(status_code=404, detail=str(e)) except Exception as e: logger.error(f"Unexpected error updating team: {e}") raise HTTPException(status_code=500, detail="Internal server error") @router.delete("/{team_id}", status_code=204) async def delete_team( team_id: str, request: Request, team_service: TeamServiceDep = Depends() ): """ Delete a team Permanently removes a team from the system. This action cannot be undone. All users associated with this team should be reassigned before deletion. Args: team_id: The team ID to delete team_service: Injected team service Returns: None (204 No Content) Raises: 400: Invalid team ID format or team has dependencies 404: Team not found 500: Internal server error """ log_request( {"path": request.url.path, "method": request.method, "team_id": team_id} ) try: await team_service.delete_team(team_id) logger.info(f"Deleted team {team_id}") return None except ValueError as e: logger.warning(f"Invalid team ID or team has dependencies: {e}") raise HTTPException(status_code=400, detail=str(e)) except RuntimeError as e: logger.warning(f"Team not found for deletion: {e}") raise HTTPException(status_code=404, detail=str(e)) except Exception as e: logger.error(f"Unexpected error deleting team: {e}") raise HTTPException(status_code=500, detail="Internal server error")