From 4327d90021e49b85e039661c55dc190a338d1e97 Mon Sep 17 00:00:00 2001 From: Zimovchik <63729114+Zimovchik@users.noreply.github.com> Date: Tue, 29 Apr 2025 17:59:41 +0300 Subject: [PATCH 1/3] new achievement logic implement --- rating_api/routes/comment.py | 32 +++++----------------- rating_api/settings.py | 14 +++++++--- rating_api/utils/achievements.py | 46 ++++++++++++++++++++++++++++++++ 3 files changed, 64 insertions(+), 28 deletions(-) create mode 100644 rating_api/utils/achievements.py diff --git a/rating_api/routes/comment.py b/rating_api/routes/comment.py index 743b9ca..8923e66 100644 --- a/rating_api/routes/comment.py +++ b/rating_api/routes/comment.py @@ -5,7 +5,7 @@ import aiohttp from auth_lib.fastapi import UnionAuth -from fastapi import APIRouter, Depends, Query +from fastapi import APIRouter, BackgroundTasks, Depends, Query from fastapi_sqlalchemy import db from rating_api.exceptions import ( @@ -31,6 +31,7 @@ CommentUpdate, ) from rating_api.settings import Settings, get_settings +from rating_api.utils.achievements import award_first_comment_achievement settings: Settings = get_settings() @@ -38,7 +39,9 @@ @comment.post("", response_model=CommentGet) -async def create_comment(lecturer_id: int, comment_info: CommentPost, user=Depends(UnionAuth())) -> CommentGet: +async def create_comment( + lecturer_id: int, comment_info: CommentPost, background_tasks: BackgroundTasks, user=Depends(UnionAuth()) +) -> CommentGet: """ Создает комментарий к преподавателю в базе данных RatingAPI Для создания комментария нужно быть авторизованным @@ -110,29 +113,8 @@ async def create_comment(lecturer_id: int, comment_info: CommentPost, user=Depen user_id=user_id, review_status=ReviewStatus.PENDING, ) - - # Выдача аччивки юзеру за первый комментарий - async with aiohttp.ClientSession() as session: - give_achievement = True - async with session.get( - settings.API_URL + f"achievement/user/{user.get('id'):}", - headers={"Accept": "application/json"}, - ) as response: - if response.status == 200: - user_achievements = await response.json() - for achievement in user_achievements.get("achievement", []): - if achievement.get("id") == settings.FIRST_COMMENT_ACHIEVEMENT_ID: - give_achievement = False - break - else: - give_achievement = False - if give_achievement: - session.post( - settings.API_URL - + f"achievement/achievement/{settings.FIRST_COMMENT_ACHIEVEMENT_ID}/reciever/{user.get('id'):}", - headers={"Accept": "application/json", "Authorization": settings.ACHIEVEMENT_GIVE_TOKEN}, - ) - + # give achievement for first comment + background_tasks.add_task(award_first_comment_achievement, user.get('id')) return CommentGet.model_validate(new_comment) diff --git a/rating_api/settings.py b/rating_api/settings.py index 63069d4..45ab491 100644 --- a/rating_api/settings.py +++ b/rating_api/settings.py @@ -22,11 +22,19 @@ class Settings(BaseSettings): CORS_ALLOW_HEADERS: list[str] = ['*'] MAX_COMMENT_LENGTH: int = 3000 - '''Temp settings''' + # Environment setting + APP_ENV: str = os.getenv("APP_ENV", "dev") # Can be "dev", "test", or "prod" + + # Achievement API settings for different environments + PROD_API_URL: str = "https://api.profcomff.com/" + TEST_API_URL: str = "https://api.test.profcomff.com/" + ACHIEVEMENT_GIVE_TOKEN: str = os.getenv("ACHIEVEMENT_API", "") + '''Temp settings''' + # For backwards compatibility API_URL: str = "https://api.test.profcomff.com/" - FIRST_COMMENT_ACHIEVEMENT_ID: int = 12 - ACHIEVEMENT_GIVE_TOKEN: str = "" + FIRST_COMMENT_ACHIEVEMENT_ID_TEST: int = 48 + FIRST_COMMENT_ACHIEVEMENT_ID_PROD: int = 12 model_config = ConfigDict(case_sensitive=True, env_file=".env", extra="ignore") diff --git a/rating_api/utils/achievements.py b/rating_api/utils/achievements.py new file mode 100644 index 0000000..9b55b04 --- /dev/null +++ b/rating_api/utils/achievements.py @@ -0,0 +1,46 @@ +import logging +from typing import Optional + +import aiohttp + +from rating_api.settings import get_settings + + +logger = logging.getLogger(__name__) +settings = get_settings() + + +async def award_first_comment_achievement(user_id: int) -> None: + # Skip in dev environment + if settings.APP_ENV not in ["prod", "test"]: + return + + if settings.APP_ENV == "prod": + api_url = settings.PROD_API_URL + achievement_id = settings.FIRST_COMMENT_ACHIEVEMENT_ID_PROD + else: + api_url = settings.TEST_API_URL + achievement_id = settings.FIRST_COMMENT_ACHIEVEMENT_ID_TEST + token = settings.ACHIEVEMENT_GIVE_TOKEN + + try: + async with aiohttp.ClientSession() as session: + # Check if user already has this achievement + + async with session.get( + api_url + f"achievement/user/{user_id}", + headers={"Accept": "application/json"}, + ) as response: + user_achievements = await response.json() + for achievement in user_achievements.get("achievement", []): + if achievement.get("id") == achievement_id: + return + + achievement_url = f"{api_url}achievement/achievement/" f"{achievement_id}/reciever/{user_id}" + + session.post( + achievement_url, + headers={"Accept": "application/json", "Authorization": token}, + ) + except Exception as e: + return From a690a125c3a77bf295e4605f6efa2f1e3d12cc93 Mon Sep 17 00:00:00 2001 From: Zimovchik <63729114+Zimovchik@users.noreply.github.com> Date: Tue, 29 Apr 2025 18:59:07 +0300 Subject: [PATCH 2/3] some changes --- rating_api/settings.py | 2 -- rating_api/utils/achievements.py | 31 ++++++++++++++----------------- 2 files changed, 14 insertions(+), 19 deletions(-) diff --git a/rating_api/settings.py b/rating_api/settings.py index 45ab491..dc36d3f 100644 --- a/rating_api/settings.py +++ b/rating_api/settings.py @@ -25,13 +25,11 @@ class Settings(BaseSettings): # Environment setting APP_ENV: str = os.getenv("APP_ENV", "dev") # Can be "dev", "test", or "prod" - # Achievement API settings for different environments PROD_API_URL: str = "https://api.profcomff.com/" TEST_API_URL: str = "https://api.test.profcomff.com/" ACHIEVEMENT_GIVE_TOKEN: str = os.getenv("ACHIEVEMENT_API", "") '''Temp settings''' - # For backwards compatibility API_URL: str = "https://api.test.profcomff.com/" FIRST_COMMENT_ACHIEVEMENT_ID_TEST: int = 48 FIRST_COMMENT_ACHIEVEMENT_ID_PROD: int = 12 diff --git a/rating_api/utils/achievements.py b/rating_api/utils/achievements.py index 9b55b04..cdfaa24 100644 --- a/rating_api/utils/achievements.py +++ b/rating_api/utils/achievements.py @@ -6,11 +6,10 @@ from rating_api.settings import get_settings -logger = logging.getLogger(__name__) settings = get_settings() -async def award_first_comment_achievement(user_id: int) -> None: +async def award_first_comment_achievement(user_id: int): # Skip in dev environment if settings.APP_ENV not in ["prod", "test"]: return @@ -23,24 +22,22 @@ async def award_first_comment_achievement(user_id: int) -> None: achievement_id = settings.FIRST_COMMENT_ACHIEVEMENT_ID_TEST token = settings.ACHIEVEMENT_GIVE_TOKEN - try: - async with aiohttp.ClientSession() as session: - # Check if user already has this achievement - - async with session.get( - api_url + f"achievement/user/{user_id}", - headers={"Accept": "application/json"}, - ) as response: + async with aiohttp.ClientSession() as session: + give_achievement = True + async with session.get( + api_url + f"achievement/user/{user_id}", + headers={"Accept": "application/json"}, + ) as response: + if response.status == 200: user_achievements = await response.json() for achievement in user_achievements.get("achievement", []): if achievement.get("id") == achievement_id: - return - - achievement_url = f"{api_url}achievement/achievement/" f"{achievement_id}/reciever/{user_id}" - + give_achievement = False + break + else: + give_achievement = False + if give_achievement: session.post( - achievement_url, + api_url + f"achievement/achievement/{achievement_id}/reciever/{user_id}", headers={"Accept": "application/json", "Authorization": token}, ) - except Exception as e: - return From 4f3fab7d71499cf45d0ce5eacf6a8a27113dbe94 Mon Sep 17 00:00:00 2001 From: Zimovchik <63729114+Zimovchik@users.noreply.github.com> Date: Tue, 29 Apr 2025 19:01:56 +0300 Subject: [PATCH 3/3] lint --- rating_api/settings.py | 1 - 1 file changed, 1 deletion(-) diff --git a/rating_api/settings.py b/rating_api/settings.py index dc36d3f..7a1b246 100644 --- a/rating_api/settings.py +++ b/rating_api/settings.py @@ -22,7 +22,6 @@ class Settings(BaseSettings): CORS_ALLOW_HEADERS: list[str] = ['*'] MAX_COMMENT_LENGTH: int = 3000 - # Environment setting APP_ENV: str = os.getenv("APP_ENV", "dev") # Can be "dev", "test", or "prod" PROD_API_URL: str = "https://api.profcomff.com/"