from datetime import datetime from fastapi import APIRouter, Depends, HTTPException, Response from typing import Optional import logging import pydantic from pandas import DataFrame from ..db_engine import db, Reward, model_to_dict, fn from ..dependencies import oauth2_scheme, valid_token, LOG_DATA logging.basicConfig( filename=LOG_DATA['filename'], format=LOG_DATA['format'], level=LOG_DATA['log_level'] ) router = APIRouter( prefix='/api/v2/rewards', tags=['rewards'] ) class RewardModel(pydantic.BaseModel): name: str season: int week: int team_id: int created: Optional[int] = int(datetime.timestamp(datetime.now())*1000) @router.get('') async def get_rewards( name: Optional[str] = None, in_name: Optional[str] = None, team_id: Optional[int] = None, season: Optional[int] = None, week: Optional[int] = None, created_after: Optional[int] = None, flat: Optional[bool] = False, csv: Optional[bool] = None): all_rewards = Reward.select() if all_rewards.count() == 0: db.close() raise HTTPException(status_code=404, detail=f'There are no rewards to filter') if name is not None: all_rewards = all_rewards.where(fn.Lower(Reward.name) == name.lower()) if team_id is not None: all_rewards = all_rewards.where(Reward.team_id == team_id) if created_after is not None: all_rewards = all_rewards.where(Reward.created >= created_after) if in_name is not None: all_rewards = all_rewards.where(fn.Lower(Reward.name).contains(in_name.lower())) if season is not None: all_rewards = all_rewards.where(Reward.season == season) if week is not None: all_rewards = all_rewards.where(Reward.week == week) if all_rewards.count() == 0: db.close() raise HTTPException(status_code=404, detail=f'No rewards found') if csv: data_list = [['id', 'name', 'team', 'daily', 'created']] for line in all_rewards: data_list.append( [ line.id, line.name, line.team.id, line.daily, line.created ] ) return_val = DataFrame(data_list).to_csv(header=False, index=False) db.close() return Response(content=return_val, media_type='text/csv') else: return_val = {'count': all_rewards.count(), 'rewards': []} for x in all_rewards: return_val['rewards'].append(model_to_dict(x, recurse=not flat)) db.close() return return_val @router.get('/{reward_id}') async def get_one_reward(reward_id, csv: Optional[bool] = False): try: this_reward = Reward.get_by_id(reward_id) except Exception: db.close() raise HTTPException(status_code=404, detail=f'No reward found with id {reward_id}') if csv: data_list = [ ['id', 'name', 'card_count', 'description'], [this_reward.id, this_reward.name, this_reward.team.id, this_reward.daily, this_reward.created] ] return_val = DataFrame(data_list).to_csv(header=False, index=False) db.close() return Response(content=return_val, media_type='text/csv') else: return_val = model_to_dict(this_reward) db.close() return return_val @router.post('') async def post_rewards(reward: RewardModel, token: str = Depends(oauth2_scheme)): if not valid_token(token): logging.warning(f'Bad Token: {token}') db.close() raise HTTPException( status_code=401, detail='You are not authorized to post rewards. This event has been logged.' ) this_reward = Reward(**reward.dict()) saved = this_reward.save() if saved == 1: return_val = model_to_dict(this_reward) db.close() return return_val else: raise HTTPException( status_code=418, detail='Well slap my ass and call me a teapot; I could not save that cardset' ) @router.patch('/{reward_id}') async def patch_reward( reward_id, name: Optional[str] = None, team_id: Optional[int] = None, created: Optional[int] = None, token: str = Depends(oauth2_scheme)): if not valid_token(token): logging.warning(f'Bad Token: {token}') db.close() raise HTTPException( status_code=401, detail='You are not authorized to patch rewards. This event has been logged.' ) try: this_reward = Reward.get_by_id(reward_id) except Exception: db.close() raise HTTPException(status_code=404, detail=f'No reward found with id {reward_id}') if name is not None: this_reward.name = name if team_id is not None: this_reward.team_id = team_id if created is not None: this_reward.created = created if this_reward.save() == 1: return_val = model_to_dict(this_reward) db.close() return return_val else: raise HTTPException( status_code=418, detail='Well slap my ass and call me a teapot; I could not save that rarity' ) @router.delete('/{reward_id}') async def delete_reward(reward_id, token: str = Depends(oauth2_scheme)): if not valid_token(token): logging.warning(f'Bad Token: {token}') db.close() raise HTTPException( status_code=401, detail='You are not authorized to delete rewards. This event has been logged.' ) try: this_reward = Reward.get_by_id(reward_id) except Exception: db.close() raise HTTPException(status_code=404, detail=f'No reward found with id {reward_id}') count = this_reward.delete_instance() db.close() if count == 1: raise HTTPException(status_code=200, detail=f'Reward {reward_id} has been deleted') else: raise HTTPException(status_code=500, detail=f'Reward {reward_id} was not deleted')