Enhance API error handling and logging in Leaderboard cog. Update authorization header format to use "Token" prefix, improve JSON response validation, and add detailed error messages for various API response statuses. Ensure robust exception handling for API requests to improve reliability and debugging.
Some checks are pending
Run pre-commit / Run pre-commit (push) Waiting to run

This commit is contained in:
Valerie 2025-05-26 09:50:08 -04:00
parent c15fb8ff47
commit 963d9e3e73

View file

@ -104,18 +104,31 @@ class Leaderboard(commands.Cog):
if self.admin_secret.get("admin_secret"):
self.session = aiohttp.ClientSession()
# Test API connection
async with self.session.get(
f"{self.api_base_url}/leaderboard",
headers={"Authorization": self.admin_secret["admin_secret"]}
) as resp:
if resp.status != 200:
log.error(f"Failed to connect to API: Status {resp.status}")
else:
# Start auto-sync task if API connection successful
self.auto_sync_task = self.bot.loop.create_task(self._auto_sync_task())
log.info("Started automatic leaderboard sync task")
try:
async with self.session.get(
f"{self.api_base_url}/leaderboard",
headers={"Authorization": f"Token {self.admin_secret['admin_secret']}"}
) as resp:
try:
data = await resp.json()
except aiohttp.ContentTypeError:
log.error("API returned invalid JSON response during initialization")
return
if resp.status == 200:
# Start auto-sync task if API connection successful
self.auto_sync_task = self.bot.loop.create_task(self._auto_sync_task())
log.info("Started automatic leaderboard sync task")
elif resp.status == 401:
log.error("Failed to initialize API: Invalid admin secret")
else:
log.error(f"Failed to initialize API: Status {resp.status}")
if data.get("error"):
log.error(f"Error message: {data['error']}")
except aiohttp.ClientError as e:
log.error(f"Failed to connect to API: {str(e)}")
except Exception as e:
log.error(f"Failed to initialize API connection: {e}")
log.error(f"Failed to initialize API connection: {str(e)}")
async def _auto_sync_task(self):
"""Task to automatically sync leaderboard every 6 hours."""
@ -251,7 +264,7 @@ class Leaderboard(commands.Cog):
async with self.session.post(
f"{self.api_base_url}/leaderboard",
headers={
"Authorization": self.admin_secret["admin_secret"],
"Authorization": f"Token {self.admin_secret['admin_secret']}",
"Content-Type": "application/json"
},
json={
@ -261,8 +274,13 @@ class Leaderboard(commands.Cog):
"optedOut": opted_out
}
) as resp:
if resp.status == 200:
try:
data = await resp.json()
except aiohttp.ContentTypeError:
log.error(f"API returned invalid JSON response with status {resp.status}")
return False
if resp.status == 200:
if data.get("success"):
log.info(f"Updated leaderboard for {username}: {credits} credits (opted_out: {opted_out})")
return True
@ -272,9 +290,14 @@ class Leaderboard(commands.Cog):
log.error("Unauthorized: Invalid admin secret")
else:
log.error(f"API update failed: Status {resp.status}")
if data.get("error"):
log.error(f"Error message: {data['error']}")
return False
except aiohttp.ClientError as e:
log.error(f"API request failed: {str(e)}")
return False
except Exception as e:
log.error(f"API update failed: {e}")
log.error(f"Unexpected error during API update: {str(e)}")
return False
async def _get_api_leaderboard(self) -> Optional[list]:
@ -285,10 +308,15 @@ class Leaderboard(commands.Cog):
try:
async with self.session.get(
f"{self.api_base_url}/leaderboard",
headers={"Authorization": self.admin_secret["admin_secret"]}
headers={"Authorization": f"Token {self.admin_secret['admin_secret']}"}
) as resp:
if resp.status == 200:
try:
data = await resp.json()
except aiohttp.ContentTypeError:
log.error(f"API returned invalid JSON response with status {resp.status}")
return None
if resp.status == 200:
if "leaderboard" in data:
return data["leaderboard"]
log.error("Invalid API response format")
@ -296,9 +324,14 @@ class Leaderboard(commands.Cog):
log.error("Unauthorized: Invalid admin secret")
else:
log.error(f"Failed to fetch leaderboard: Status {resp.status}")
if data.get("error"):
log.error(f"Error message: {data['error']}")
return None
except aiohttp.ClientError as e:
log.error(f"Error fetching leaderboard: {str(e)}")
return None
except Exception as e:
log.error(f"Error fetching leaderboard: {e}")
log.error(f"Unexpected error fetching leaderboard: {str(e)}")
return None
@commands.group(name="globalboard", aliases=["glb"])