Skip to content

Commit

Permalink
Merge pull request #706 from Path-of-Modifiers/705-remove-account-fea…
Browse files Browse the repository at this point in the history
…ture

705 remove account feature
  • Loading branch information
Ivareh authored Nov 24, 2024
2 parents 9179351 + f321004 commit 1dd800d
Show file tree
Hide file tree
Showing 68 changed files with 367 additions and 6,542 deletions.
11 changes: 4 additions & 7 deletions src/backend_api/app/api/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,6 @@
test_prefix,
turnstile,
turnstile_prefix,
user,
user_prefix,
)

api_router = APIRouter()
Expand All @@ -42,9 +40,6 @@
api_router.include_router(
item.router, prefix=f"/{item_prefix}", tags=[f"{item_prefix}s"]
)
api_router.include_router(
login.router, prefix=f"/{login_prefix}", tags=[f"{login_prefix}s"]
)
api_router.include_router(
modifier.router, prefix=f"/{modifier_prefix}", tags=[f"{modifier_prefix}s"]
)
Expand All @@ -55,8 +50,10 @@
turnstile.router, prefix=f"/{turnstile_prefix}", tags=[f"{turnstile_prefix}s"]
)
api_router.include_router(
user.router, prefix=f"/{user_prefix}", tags=[f"{user_prefix}s"]
test.router, prefix=f"/{test_prefix}", tags=[f"{test_prefix}s"]
)
api_router.include_router(
test.router, prefix=f"/{test_prefix}", tags=[f"{test_prefix}s"]
login.router,
prefix=f"/{login_prefix}",
tags=[f"{login_prefix}s"],
)
4 changes: 0 additions & 4 deletions src/backend_api/app/api/routes/item.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,12 @@
from sqlalchemy.orm import Session

import app.core.schemas as schemas
from app.api.api_message_util import (
get_delete_return_msg,
)
from app.api.deps import (
get_current_active_superuser,
get_current_active_user,
get_db,
)
from app.api.params import FilterParams
from app.core.models.models import Item
from app.core.rate_limit.rate_limit_config import rate_limit_settings
from app.core.rate_limit.rate_limiters import apply_user_rate_limits
from app.crud import CRUD_item
Expand Down
4 changes: 2 additions & 2 deletions src/backend_api/app/api/routes/item_base_type.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
from app.core.models.models import ItemBaseType
from app.core.rate_limit.rate_limit_config import rate_limit_settings
from app.core.rate_limit.rate_limiters import (
apply_ip_rate_limits,
apply_user_rate_limits,
)
from app.crud import CRUD_itemBaseType
Expand Down Expand Up @@ -58,9 +59,8 @@ async def get_item_base_type(
@router.get(
"/",
response_model=schemas.ItemBaseType | list[schemas.ItemBaseType],
dependencies=[Depends(get_current_active_user)],
)
@apply_user_rate_limits(
@apply_ip_rate_limits(
rate_limit_settings.DEFAULT_USER_RATE_LIMIT_SECOND,
rate_limit_settings.DEFAULT_USER_RATE_LIMIT_MINUTE,
rate_limit_settings.DEFAULT_USER_RATE_LIMIT_HOUR,
Expand Down
160 changes: 2 additions & 158 deletions src/backend_api/app/api/routes/login.py
Original file line number Diff line number Diff line change
@@ -1,45 +1,23 @@
# From FastAPI Fullstack Template https://github.com/fastapi/full-stack-fastapi-template/blob/master/backend/app/api/routes/login.py
from typing import Annotated, Any
from typing import Annotated

from fastapi import APIRouter, Depends, Request, Response
from fastapi.responses import HTMLResponse
from fastapi.security import OAuth2PasswordRequestForm
from pydantic import EmailStr
from sqlalchemy.orm import Session

from app.api.api_message_util import (
get_password_rec_email_sent_success_msg,
get_user_psw_change_msg,
)
from app.api.deps import (
UserCachePasswordResetSession,
UserCacheSession,
get_current_active_superuser,
get_db,
)
from app.core.config import settings
from app.core.models.models import User
from app.core.rate_limit.rate_limit_config import rate_limit_settings
from app.core.rate_limit.rate_limiters import (
apply_ip_rate_limits,
)
from app.core.schemas import Message, NewPassword, Token
from app.core.schemas.token import RecoverPassword
from app.core.security import (
get_password_hash,
verify_password,
)
from app.core.schemas import Token
from app.crud import CRUD_user
from app.exceptions import (
BadLoginCredentialsError,
DbObjectDoesNotExistError,
EmailOrUsernameRequiredError,
InvalidTokenError,
NewPasswordIsSameError,
)
from app.utils.user import (
generate_reset_password_email,
send_email,
)

router = APIRouter()
Expand Down Expand Up @@ -81,137 +59,3 @@ async def login_access_session(
return Token(
access_token=access_token,
)


@router.post("/password-recovery/")
@apply_ip_rate_limits(
rate_limit_settings.RECOVERY_PASSWORD_RATE_LIMIT_SECOND,
rate_limit_settings.RECOVERY_PASSWORD_RATE_LIMIT_MINUTE,
rate_limit_settings.RECOVERY_PASSWORD_RATE_LIMIT_HOUR,
rate_limit_settings.RECOVERY_PASSWORD_RATE_LIMIT_DAY,
)
async def recover_password(
request: Request, # noqa: ARG001
response: Response, # noqa: ARG001
body: RecoverPassword,
user_cache_password_reset: UserCachePasswordResetSession,
db: Session = Depends(get_db),
) -> Message:
"""
Password Recovery
"""
if not body.email and not body.username:
raise EmailOrUsernameRequiredError(
function_name=recover_password.__name__,
)
get_user_filter = {}
if body.email:
get_user_filter["email"] = body.email
if body.username:
get_user_filter["username"] = body.username
user = CRUD_user.get(db=db, filter=get_user_filter)
if not user:
raise DbObjectDoesNotExistError(
model_table_name=User.__tablename__,
filter=get_user_filter,
function_name=recover_password.__name__,
)

password_reset_token = await user_cache_password_reset.create_user_cache_instance(
user=user, expire_seconds=settings.EMAIL_RESET_TOKEN_EXPIRE_SECONDS
)

if not body.email:
email = CRUD_user.get_email_by_username(db=db, username=body.username)
else:
email = body.email

email_data = generate_reset_password_email(
email_to=user.email, email=email, token=password_reset_token
)
send_email(
email_to=user.email,
subject=email_data.subject,
html_content=email_data.html_content,
)
return get_password_rec_email_sent_success_msg()


@router.post("/reset-password/")
@apply_ip_rate_limits(
rate_limit_settings.RESET_PASSWORD_RATE_LIMIT_SECOND,
rate_limit_settings.RESET_PASSWORD_RATE_LIMIT_MINUTE,
rate_limit_settings.RESET_PASSWORD_RATE_LIMIT_HOUR,
rate_limit_settings.RESET_PASSWORD_RATE_LIMIT_DAY,
)
async def reset_password(
request: Request, # noqa: ARG001
response: Response, # noqa: ARG001
body: NewPassword,
user_cache_password_reset: UserCachePasswordResetSession,
db: Session = Depends(get_db),
) -> Message:
"""
Reset password
"""
cached_user = await user_cache_password_reset.verify_token(token=body.token)

email = cached_user.email
if not email:
raise InvalidTokenError(
token=body.token,
function_name=reset_password.__name__,
)
get_user_filter = {"email": email}
user = CRUD_user.get(db=db, filter=get_user_filter)
if not user:
raise DbObjectDoesNotExistError(
model_table_name=User.__tablename__,
filter=get_user_filter,
function_name=reset_password.__name__,
)
if verify_password(body.new_password, user.hashedPassword):
raise NewPasswordIsSameError(
function_name=reset_password.__name__,
)
hashed_password = get_password_hash(password=body.new_password)
user.hashedPassword = hashed_password
db.add(user)
db.commit()
db.refresh(user)
return get_user_psw_change_msg(user.username)


@router.post(
"/password-recovery-html-content/{email}",
dependencies=[Depends(get_current_active_superuser)],
response_class=HTMLResponse,
)
async def recover_password_html_content(
email: EmailStr,
user_cache_password_reset: UserCachePasswordResetSession,
db: Session = Depends(get_db),
) -> Any:
"""
HTML Content for Password Recovery
"""
filter = {"email": email}
user = CRUD_user.get(db=db, filter=filter)

if not user:
raise DbObjectDoesNotExistError(
model_table_name=User.__tablename__,
filter=filter,
function_name=recover_password_html_content.__name__,
)
password_reset_token = await user_cache_password_reset.create_user_cache_instance(
user=user, expire_seconds=settings.EMAIL_RESET_TOKEN_EXPIRE_SECONDS
)

email_data = generate_reset_password_email(
email_to=user.email, email=email, token=password_reset_token
)

return HTMLResponse(
content=email_data.html_content, headers={"subject:": email_data.subject}
)
8 changes: 5 additions & 3 deletions src/backend_api/app/api/routes/modifier.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,10 @@
from app.api.params import FilterParams
from app.core.models.models import Modifier
from app.core.rate_limit.rate_limit_config import rate_limit_settings
from app.core.rate_limit.rate_limiters import apply_user_rate_limits
from app.core.rate_limit.rate_limiters import (
apply_ip_rate_limits,
apply_user_rate_limits,
)
from app.crud import CRUD_modifier

router = APIRouter()
Expand Down Expand Up @@ -88,9 +91,8 @@ async def get_all_modifiers(
"/grouped_modifiers_by_effect/",
response_model=schemas.GroupedModifierByEffect
| list[schemas.GroupedModifierByEffect],
dependencies=[Depends(get_current_active_user)],
)
@apply_user_rate_limits(
@apply_ip_rate_limits(
rate_limit_settings.DEFAULT_USER_RATE_LIMIT_SECOND,
rate_limit_settings.DEFAULT_USER_RATE_LIMIT_MINUTE,
rate_limit_settings.DEFAULT_USER_RATE_LIMIT_HOUR,
Expand Down
14 changes: 2 additions & 12 deletions src/backend_api/app/api/routes/plot.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,8 @@
from sqlalchemy.ext.asyncio import AsyncSession

from app.api.deps import (
UserCacheSession,
get_async_current_active_user,
get_async_db,
get_rate_limit_tier_by_request,
get_user_ip_from_header,
get_username_by_request,
)
from app.core.rate_limit.custom_rate_limiter import RateSpec
from app.core.rate_limit.rate_limit_config import rate_limit_settings
Expand All @@ -23,12 +19,10 @@
@router.post(
"/",
response_model=PlotData,
dependencies=[Depends(get_async_current_active_user)],
)
async def get_plot_data(
request: Request,
query: PlotQuery,
user_cache_session: UserCacheSession,
db: AsyncSession = Depends(get_async_db),
):
"""
Expand All @@ -37,19 +31,15 @@ async def get_plot_data(
The 'PlotQuery' schema allows for modifier restriction and item specifications.
"""
rate_limit_tier = await get_rate_limit_tier_by_request(request, user_cache_session)
request_limit = rate_limit_settings.TIER_0_PLOT_RATE_LIMIT
rate_spec = RateSpec(
requests=rate_limit_tier,
requests=request_limit,
cooldown_seconds=rate_limit_settings.PLOT_RATE_LIMIT_COOLDOWN_SECONDS,
)

client_ip = get_user_ip_from_header(request)

async with apply_custom_rate_limit(
unique_key="plot_" + get_username_by_request(request),
rate_spec=rate_spec,
prefix=plot_prefix,
), apply_custom_rate_limit(
unique_key="plot_" + client_ip,
rate_spec=rate_spec,
prefix=plot_prefix,
Expand Down
2 changes: 0 additions & 2 deletions src/backend_api/app/core/schemas/currency.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
import datetime as _dt

import pydantic as _pydantic


Expand Down
2 changes: 0 additions & 2 deletions src/backend_api/app/core/schemas/item_modifier.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
import datetime as _dt

import pydantic as _pydantic


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,6 @@
from app.core.models.models import Currency
from app.crud import CRUD_currency
from app.crud.base import CRUDBase, ModelType
from app.tests.test_simulating_env.api.api_routes_test_slowapi_rate_limit import (
TestRateLimitSlowAPI as RateLimitSlowAPITestClass,
)
from app.tests.utils.model_utils.currency import (
create_random_currency_dict,
generate_random_currency,
Expand Down Expand Up @@ -135,5 +132,5 @@ class TestCurrency(test_api.TestAPI):
pass


class TestCurrencyRateLimit(RateLimitSlowAPITestClass):
pass
# class TestCurrencyRateLimit(RateLimitSlowAPITestClass):
# pass
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,6 @@
from app.core.models.models import ItemBaseType as model_ItemBaseType
from app.crud import CRUD_itemBaseType
from app.crud.base import CRUDBase, ModelType
from app.tests.test_simulating_env.api.api_routes_test_slowapi_rate_limit import (
TestRateLimitSlowAPI as RateLimitSlowAPITestClass,
)
from app.tests.utils.model_utils.item_base_type import (
create_random_item_base_type_dict,
generate_random_item_base_type,
Expand Down Expand Up @@ -132,5 +129,5 @@ class TestItemBaseType(test_api.TestAPI):
pass


class TestItemBaseTypeRateLimit(RateLimitSlowAPITestClass):
pass
# class TestItemBaseTypeRateLimit(RateLimitSlowAPITestClass):
# pass
Loading

0 comments on commit 1dd800d

Please sign in to comment.