"""Outbound notifications. Extracted from app/routes/users.py, where it sat between two route definitions and pulled `requests`, `logging` and the Discord bot into a module whose subject is HTTP handlers (ARCH-003). Every failure here is swallowed and logged on purpose: a notification that does not reach Discord must not roll back the session it was announcing. That is the one place in this codebase where `except Exception` is the right answer rather than an oversight. """ import logging import os import requests logger = logging.getLogger(__name__) #: Either a webhook URL, or a bare Discord user id to DM instead. DISCORD_WEBHOOK_URL = os.environ.get('DISCORD_WEBHOOK_URL', '') def send_discord_notification( player_name, points, date_str, start_time_str, end_time_str, team_name, coach_name, coach_discord, coach_discord_id, request_id=None, ): """Send a Discord notification for a One on One request. Args: player_name: Who is asking. points: Free-text discussion points, possibly empty. date_str, start_time_str, end_time_str: Already formatted for display. team_name: The player's team, or None. coach_name: Who is being asked. coach_discord: The coach's Discord handle, for the webhook footer. coach_discord_id: The coach's Discord snowflake, for a direct message. request_id: OneOnOneRequest primary key, so reactions can find it back. """ if coach_discord_id: try: from app.discord_bot import send_one_on_one_dm send_one_on_one_dm( coach_name=coach_name, coach_discord_id=coach_discord_id, player_name=player_name, team_name=team_name, date_str=date_str, start_time=start_time_str, end_time=end_time_str, points=points, request_id=request_id, ) except Exception as e: logger.warning(f"Failed to send Discord DM: {e}") if DISCORD_WEBHOOK_URL: try: from app.discord_bot import send_one_on_one_dm if DISCORD_WEBHOOK_URL.isdigit() and not coach_discord_id: send_one_on_one_dm( coach_name=coach_name, coach_discord_id=DISCORD_WEBHOOK_URL, player_name=player_name, team_name=team_name, date_str=date_str, start_time=start_time_str, end_time=end_time_str, points=points, ) elif not DISCORD_WEBHOOK_URL.isdigit(): embed = { "embeds": [ { "title": "One on One Request", "color": 3447003, "fields": [ {"name": "Player", "value": player_name, "inline": True}, { "name": "Team", "value": team_name or "Unknown Team", "inline": True, }, {"name": "Date", "value": date_str, "inline": True}, { "name": "Time", "value": f"{start_time_str} - {end_time_str}", "inline": True, }, { "name": "Discussion Points", "value": points or "No specific points provided", "inline": False, }, ], "footer": { "text": f"Coach: {coach_name}" + (f" (Discord: {coach_discord})" if coach_discord else ""), }, } ], } requests.post(DISCORD_WEBHOOK_URL, json=embed, timeout=5) except Exception as e: logger.warning(f"Failed to send Discord notification: {e}")