diff --git a/lnbits/core/crud/users.py b/lnbits/core/crud/users.py index 45248bd4c..fc68162a1 100644 --- a/lnbits/core/crud/users.py +++ b/lnbits/core/crud/users.py @@ -98,19 +98,17 @@ async def get_accounts( async def get_account( - user_id: str, activated: bool | None = True, conn: Connection | None = None + user_id: str, active_only: bool = True, conn: Connection | None = None ) -> Account | None: if len(user_id) == 0: return None - activate_clause = "" if activated is None else "AND activated = :activated" - return await (conn or db).fetchone( - f""" + """ SELECT * FROM accounts - WHERE id = :id {activate_clause} - """, # noqa: S608 - {"id": user_id, "activated": activated}, + WHERE id = :id AND (activated = true OR activated = :activated) + """, + {"id": user_id, "activated": active_only}, Account, ) @@ -136,7 +134,7 @@ async def delete_accounts_no_wallets( async def get_account_by_username( - username: str, activated: bool = True, conn: Connection | None = None + username: str, active_only: bool = True, conn: Connection | None = None ) -> Account | None: if len(username) == 0: return None @@ -144,28 +142,32 @@ async def get_account_by_username( return await (conn or db).fetchone( """ SELECT * FROM accounts - WHERE LOWER(username) = :username AND activated = :activated + WHERE + LOWER(username) = :username + AND (activated = true OR activated = :activated) """, - {"username": username.lower(), "activated": activated}, + {"username": username.lower(), "activated": active_only}, Account, ) async def get_account_by_pubkey( - pubkey: str, activated: bool | None = True, conn: Connection | None = None + pubkey: str, active_only: bool = True, conn: Connection | None = None ) -> Account | None: return await (conn or db).fetchone( """ SELECT * FROM accounts - WHERE LOWER(pubkey) = :pubkey AND activated = :activated + WHERE + LOWER(pubkey) = :pubkey + AND (activated = true OR activated = :activated) """, - {"pubkey": pubkey.lower(), "activated": activated}, + {"pubkey": pubkey.lower(), "activated": active_only}, Account, ) async def get_account_by_email( - email: str, activated: bool = True, conn: Connection | None = None + email: str, active_only: bool = True, conn: Connection | None = None ) -> Account | None: if len(email) == 0: return None @@ -173,35 +175,38 @@ async def get_account_by_email( return await (conn or db).fetchone( """ SELECT * FROM accounts - WHERE LOWER(email) = :email AND activated = :activated + WHERE + LOWER(email) = :email + AND (activated = true OR activated = :activated) """, - {"email": email.lower(), "activated": activated}, + {"email": email.lower(), "activated": active_only}, Account, ) async def get_account_by_username_or_email( username_or_email: str, - activated: bool = True, + active_only: bool = True, conn: Connection | None = None, ) -> Account | None: return await (conn or db).fetchone( """ SELECT * FROM accounts - WHERE (LOWER(email) = :value or LOWER(username) = :value) - AND activated = :activated + WHERE + (LOWER(email) = :value or LOWER(username) = :value) + AND (activated = true OR activated = :activated) """, - {"value": username_or_email.lower(), "activated": activated}, + {"value": username_or_email.lower(), "activated": active_only}, Account, ) async def get_user( - user_id: str, activated: bool | None = True, conn: Connection | None = None + user_id: str, active_only: bool = True, conn: Connection | None = None ) -> User | None: async with db.reuse_conn(conn) if conn else db.connect() as conn: - account = await get_account(user_id, activated=activated, conn=conn) + account = await get_account(user_id, active_only, conn=conn) if not account: return None return await get_user_from_account(account, conn=conn) @@ -246,14 +251,14 @@ async def update_user_access_control_list( async def get_user_access_control_lists( - user_id: str, activated: bool = True, conn: Connection | None = None + user_id: str, active_only: bool = True, conn: Connection | None = None ) -> UserAcls: user_acls = await (conn or db).fetchone( """ SELECT id, access_control_list FROM accounts - WHERE id = :user_id AND activated = :activated + WHERE id = :user_id AND (activated = true OR activated = :activated) """, - {"user_id": user_id, "activated": activated}, + {"user_id": user_id, "activated": active_only}, UserAcls, ) @@ -261,7 +266,7 @@ async def get_user_access_control_lists( async def clear_user_id_cache(user_id: str): - user = await get_user(user_id, activated=None) + user = await get_user(user_id, active_only=True) if user: clear_user_cache(user) diff --git a/lnbits/core/views/auth_api.py b/lnbits/core/views/auth_api.py index c8330416c..101d65b92 100644 --- a/lnbits/core/views/auth_api.py +++ b/lnbits/core/views/auth_api.py @@ -95,7 +95,7 @@ async def nostr_login(request: Request) -> JSONResponse: if not settings.is_auth_method_allowed(AuthMethods.nostr_auth_nip98): raise HTTPException(HTTPStatus.FORBIDDEN, "Login with Nostr Auth not allowed.") event = _nostr_nip98_event(request) - account = await get_account_by_pubkey(event["pubkey"]) + account = await get_account_by_pubkey(event["pubkey"], active_only=False) if not account: account = Account( id=uuid4().hex, @@ -103,6 +103,8 @@ async def nostr_login(request: Request) -> JSONResponse: extra=UserExtra(provider="nostr"), ) await create_user_account(account) + if not account.activated: + raise HTTPException(HTTPStatus.UNAUTHORIZED, "User is not activated.") return _auth_success_response(account.username or "", account.id, account.email) @@ -358,7 +360,7 @@ async def register(data: RegisterUser) -> JSONResponse: if not is_valid_username(data.username): raise HTTPException(HTTPStatus.BAD_REQUEST, "Invalid username.") - if await get_account_by_username(data.username): + if await get_account_by_username(data.username, active_only=False): raise HTTPException(HTTPStatus.BAD_REQUEST, "Username already exists.") if data.email and not is_valid_email_address(data.email): @@ -528,7 +530,7 @@ async def _handle_sso_login(userinfo: OpenID, verified_user_id: str | None = Non raise HTTPException(HTTPStatus.BAD_REQUEST, "Invalid email.") redirect_path = "/wallet" - account = await get_account_by_email(email) + account = await get_account_by_email(email, active_only=False) if verified_user_id: if account: diff --git a/lnbits/core/views/user_api.py b/lnbits/core/views/user_api.py index 82b277458..dd500766b 100644 --- a/lnbits/core/views/user_api.py +++ b/lnbits/core/views/user_api.py @@ -74,7 +74,7 @@ async def api_get_users( summary="Get user by Id", ) async def api_get_user(user_id: str) -> User: - user = await get_user(user_id, activated=None) + user = await get_user(user_id, active_only=False) if not user: raise HTTPException(HTTPStatus.NOT_FOUND, "User not found.") return user @@ -242,7 +242,7 @@ async def api_users_toggle_activated( if settings.is_admin_user(user_id): settings.lnbits_admin_users.remove(user_id) - user_account = await get_account(user_id, activated=None) + user_account = await get_account(user_id, active_only=False) if not user_account: raise HTTPException( status_code=HTTPStatus.NOT_FOUND,