From 3818dba635705d747b7da84fe8ab4dc2c5dcc9ab Mon Sep 17 00:00:00 2001 From: Andrew Smith Date: Thu, 7 Dec 2023 01:37:10 +0000 Subject: [PATCH 1/2] feat: add sign_out() scope option --- gotrue/_async/gotrue_admin_api.py | 5 +++-- gotrue/_async/gotrue_client.py | 10 ++++++---- gotrue/_sync/gotrue_admin_api.py | 5 +++-- gotrue/_sync/gotrue_client.py | 10 ++++++---- gotrue/types.py | 7 +++++++ 5 files changed, 25 insertions(+), 12 deletions(-) diff --git a/gotrue/_async/gotrue_admin_api.py b/gotrue/_async/gotrue_admin_api.py index 3572e04b..e7c8d250 100644 --- a/gotrue/_async/gotrue_admin_api.py +++ b/gotrue/_async/gotrue_admin_api.py @@ -14,6 +14,7 @@ GenerateLinkParams, GenerateLinkResponse, Options, + SignOutScope, User, UserResponse, ) @@ -39,13 +40,13 @@ def __init__( self.mfa.list_factors = self._list_factors self.mfa.delete_factor = self._delete_factor - async def sign_out(self, jwt: str) -> None: + async def sign_out(self, jwt: str, scope: SignOutScope = "global") -> None: """ Removes a logged-in session. """ return await self._request( "POST", - "logout", + f"logout?scope={scope}", jwt=jwt, no_resolve_json=True, ) diff --git a/gotrue/_async/gotrue_client.py b/gotrue/_async/gotrue_client.py index 2140ff9c..06be518d 100644 --- a/gotrue/_async/gotrue_client.py +++ b/gotrue/_async/gotrue_client.py @@ -60,6 +60,7 @@ SignInWithOAuthCredentials, SignInWithPasswordCredentials, SignInWithPasswordlessCredentials, + SignOutOptions, SignUpWithPasswordCredentials, Subscription, UserAttributes, @@ -480,7 +481,7 @@ async def refresh_session( session = await self._call_refresh_token(refresh_token) return AuthResponse(session=session, user=session.user) - async def sign_out(self) -> None: + async def sign_out(self, options: SignOutOptions = {"scope": "global"}) -> None: """ Inside a browser context, `sign_out` will remove the logged in user from the browser session and log them out - removing all items from localstorage and @@ -496,10 +497,11 @@ async def sign_out(self) -> None: session = await self.get_session() access_token = session.access_token if session else None if access_token: - await self.admin.sign_out(access_token) + await self.admin.sign_out(access_token, options["scope"]) - await self._remove_session() - self._notify_all_subscribers("SIGNED_OUT", None) + if options["scope"] != "others": + await self._remove_session() + self._notify_all_subscribers("SIGNED_OUT", None) def on_auth_state_change( self, diff --git a/gotrue/_sync/gotrue_admin_api.py b/gotrue/_sync/gotrue_admin_api.py index 388c7c97..ebe54a08 100644 --- a/gotrue/_sync/gotrue_admin_api.py +++ b/gotrue/_sync/gotrue_admin_api.py @@ -14,6 +14,7 @@ GenerateLinkParams, GenerateLinkResponse, Options, + SignOutScope, User, UserResponse, ) @@ -39,13 +40,13 @@ def __init__( self.mfa.list_factors = self._list_factors self.mfa.delete_factor = self._delete_factor - def sign_out(self, jwt: str) -> None: + def sign_out(self, jwt: str, scope: SignOutScope = "global") -> None: """ Removes a logged-in session. """ return self._request( "POST", - "logout", + f"logout?scope={scope}", jwt=jwt, no_resolve_json=True, ) diff --git a/gotrue/_sync/gotrue_client.py b/gotrue/_sync/gotrue_client.py index 12500a1b..4c270bc4 100644 --- a/gotrue/_sync/gotrue_client.py +++ b/gotrue/_sync/gotrue_client.py @@ -60,6 +60,7 @@ SignInWithOAuthCredentials, SignInWithPasswordCredentials, SignInWithPasswordlessCredentials, + SignOutOptions, SignUpWithPasswordCredentials, Subscription, UserAttributes, @@ -478,7 +479,7 @@ def refresh_session(self, refresh_token: Union[str, None] = None) -> AuthRespons session = self._call_refresh_token(refresh_token) return AuthResponse(session=session, user=session.user) - def sign_out(self) -> None: + def sign_out(self, options: SignOutOptions = {"scope": "global"}) -> None: """ Inside a browser context, `sign_out` will remove the logged in user from the browser session and log them out - removing all items from localstorage and @@ -494,10 +495,11 @@ def sign_out(self) -> None: session = self.get_session() access_token = session.access_token if session else None if access_token: - self.admin.sign_out(access_token) + self.admin.sign_out(access_token, options["scope"]) - self._remove_session() - self._notify_all_subscribers("SIGNED_OUT", None) + if options["scope"] != "others": + self._remove_session() + self._notify_all_subscribers("SIGNED_OUT", None) def on_auth_state_change( self, diff --git a/gotrue/types.py b/gotrue/types.py index 1f09a3f1..b47c2084 100644 --- a/gotrue/types.py +++ b/gotrue/types.py @@ -650,6 +650,13 @@ class DecodedJWTDict(TypedDict): amr: NotRequired[Union[List[AMREntry], None]] +SignOutScope = Literal["global", "local", "others"] + + +class SignOutOptions(TypedDict): + scope: NotRequired[SignOutScope] + + for model in [ AMREntry, AuthResponse, From 34a3ddfe8b9343c15b6959338a353aeb5e530b70 Mon Sep 17 00:00:00 2001 From: Andrew Smith Date: Thu, 7 Dec 2023 10:00:59 +0000 Subject: [PATCH 2/2] Update to use query property of the request method --- gotrue/_async/gotrue_admin_api.py | 3 ++- gotrue/_sync/gotrue_admin_api.py | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/gotrue/_async/gotrue_admin_api.py b/gotrue/_async/gotrue_admin_api.py index e7c8d250..b4eb655d 100644 --- a/gotrue/_async/gotrue_admin_api.py +++ b/gotrue/_async/gotrue_admin_api.py @@ -46,7 +46,8 @@ async def sign_out(self, jwt: str, scope: SignOutScope = "global") -> None: """ return await self._request( "POST", - f"logout?scope={scope}", + "logout", + query={"scope": scope}, jwt=jwt, no_resolve_json=True, ) diff --git a/gotrue/_sync/gotrue_admin_api.py b/gotrue/_sync/gotrue_admin_api.py index ebe54a08..9ae7f9c8 100644 --- a/gotrue/_sync/gotrue_admin_api.py +++ b/gotrue/_sync/gotrue_admin_api.py @@ -46,7 +46,8 @@ def sign_out(self, jwt: str, scope: SignOutScope = "global") -> None: """ return self._request( "POST", - f"logout?scope={scope}", + "logout", + query={"scope": scope}, jwt=jwt, no_resolve_json=True, )