Skip to content

fix: handle tenant not found error #403

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 18 additions & 16 deletions supertokens_python/recipe/multitenancy/api/implementation.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,16 @@ async def login_methods_get(
api_options: APIOptions,
user_context: Dict[str, Any],
) -> Union[LoginMethodsGetOkResult, GeneralErrorResponse]:
tenant_config_res = await api_options.recipe_implementation.get_tenant(

tenant_config = await api_options.recipe_implementation.get_tenant(
tenant_id, user_context
)

if tenant_config is None:
raise Exception("Tenant not found")

provider_inputs_from_static = api_options.static_third_party_providers
provider_configs_from_core = tenant_config_res.third_party.providers
provider_configs_from_core = tenant_config.third_party.providers

merged_providers = merge_providers_from_core_and_static(
provider_configs_from_core, provider_inputs_from_static
Expand All @@ -61,24 +65,22 @@ async def login_methods_get(
client_type,
user_context,
)
final_provider_list.append(
ThirdPartyProvider(
provider_instance.id, provider_instance.config.name
)
)
except Exception as e:
if isinstance(e, ClientTypeNotFoundError):
continue
raise e

if provider_instance is None:
raise Exception("Should never come here")

except ClientTypeNotFoundError:
continue
final_provider_list.append(
ThirdPartyProvider(provider_instance.id, provider_instance.config.name)
)

return LoginMethodsGetOkResult(
email_password=LoginMethodEmailPassword(
tenant_config_res.emailpassword.enabled
),
passwordless=LoginMethodPasswordless(
tenant_config_res.passwordless.enabled
tenant_config.emailpassword.enabled
),
passwordless=LoginMethodPasswordless(tenant_config.passwordless.enabled),
third_party=LoginMethodThirdParty(
tenant_config_res.third_party.enabled, final_provider_list
tenant_config.third_party.enabled, final_provider_list
),
)
2 changes: 1 addition & 1 deletion supertokens_python/recipe/multitenancy/asyncio/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ async def delete_tenant(

async def get_tenant(
tenant_id: str, user_context: Optional[Dict[str, Any]] = None
) -> GetTenantOkResult:
) -> Optional[GetTenantOkResult]:
if user_context is None:
user_context = {}
recipe = MultitenancyRecipe.get_instance()
Expand Down
2 changes: 1 addition & 1 deletion supertokens_python/recipe/multitenancy/interfaces.py
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ async def delete_tenant(
@abstractmethod
async def get_tenant(
self, tenant_id: str, user_context: Dict[str, Any]
) -> GetTenantOkResult:
) -> Optional[GetTenantOkResult]:
pass

@abstractmethod
Expand Down
62 changes: 1 addition & 61 deletions supertokens_python/recipe/multitenancy/recipe.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@
from ...post_init_callbacks import PostSTInitCallbacks

from .interfaces import (
APIInterface,
APIOptions,
TypeGetAllowedDomainsForTenantId,
)
Expand All @@ -42,19 +41,12 @@

from supertokens_python.normalised_url_path import NormalisedURLPath
from supertokens_python.querier import Querier
from supertokens_python.types import GeneralErrorResponse
from supertokens_python.recipe.multitenancy.api.implementation import APIImplementation


from .api import handle_login_methods_api
from .constants import LOGIN_METHODS
from .exceptions import MultitenancyError
from .interfaces import (
LoginMethodsGetOkResult,
ThirdPartyProvider,
LoginMethodEmailPassword,
LoginMethodPasswordless,
LoginMethodThirdParty,
)
from .utils import (
InputOverrideConfig,
validate_and_normalise_user_input,
Expand Down Expand Up @@ -196,58 +188,6 @@ def reset():
MultitenancyRecipe.__instance = None


class APIImplementation(APIInterface):
async def login_methods_get(
self,
tenant_id: str,
client_type: Optional[str],
api_options: APIOptions,
user_context: Dict[str, Any],
) -> Union[LoginMethodsGetOkResult, GeneralErrorResponse]:
from supertokens_python.recipe.thirdparty.providers.config_utils import (
find_and_create_provider_instance,
merge_providers_from_core_and_static,
)
from supertokens_python.recipe.thirdparty.exceptions import (
ClientTypeNotFoundError,
)

tenant_config = await api_options.recipe_implementation.get_tenant(
tenant_id, user_context
)

provider_inputs_from_static = api_options.static_third_party_providers
provider_configs_from_core = tenant_config.third_party.providers

merged_providers = merge_providers_from_core_and_static(
provider_configs_from_core, provider_inputs_from_static
)

final_provider_list: List[ThirdPartyProvider] = []

for provider_input in merged_providers:
try:
provider_instance = await find_and_create_provider_instance(
merged_providers,
provider_input.config.third_party_id,
client_type,
user_context,
)
except ClientTypeNotFoundError:
continue
final_provider_list.append(
ThirdPartyProvider(provider_instance.id, provider_instance.config.name)
)

return LoginMethodsGetOkResult(
LoginMethodEmailPassword(tenant_config.emailpassword.enabled),
LoginMethodPasswordless(tenant_config.passwordless.enabled),
LoginMethodThirdParty(
tenant_config.third_party.enabled, final_provider_list
),
)


class AllowedDomainsClaimClass(PrimitiveArrayClaim[List[str]]):
def __init__(self):
default_max_age_in_sec = 60 * 60
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -160,13 +160,16 @@ async def delete_tenant(

async def get_tenant(
self, tenant_id: Optional[str], user_context: Dict[str, Any]
) -> GetTenantOkResult:
) -> Optional[GetTenantOkResult]:
res = await self.querier.send_get_request(
NormalisedURLPath(
f"{tenant_id or DEFAULT_TENANT_ID}/recipe/multitenancy/tenant"
),
)

if res["status"] == "TENANT_NOT_FOUND_ERROR":
return None

tenant_config = parse_tenant_config(res)

return GetTenantOkResult(
Expand Down
9 changes: 7 additions & 2 deletions supertokens_python/recipe/thirdparty/api/authorisation_url.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
if TYPE_CHECKING:
from supertokens_python.recipe.thirdparty.interfaces import APIOptions, APIInterface

from supertokens_python.exceptions import raise_bad_input_exception
from supertokens_python.exceptions import raise_bad_input_exception, BadInputError
from supertokens_python.utils import send_200_response


Expand Down Expand Up @@ -53,7 +53,12 @@ async def handle_authorisation_url_api(
user_context=user_context,
)

provider = provider_response.provider
if provider_response is None:
raise BadInputError(
f"the provider {third_party_id} could not be found in the configuration"
)

provider = provider_response
result = await api_implementation.authorisation_url_get(
provider=provider,
redirect_uri_on_provider_dashboard=redirect_uri_on_provider_dashboard,
Expand Down
9 changes: 7 additions & 2 deletions supertokens_python/recipe/thirdparty/api/signinup.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
if TYPE_CHECKING:
from supertokens_python.recipe.thirdparty.interfaces import APIOptions, APIInterface

from supertokens_python.exceptions import raise_bad_input_exception
from supertokens_python.exceptions import raise_bad_input_exception, BadInputError
from supertokens_python.utils import send_200_response


Expand Down Expand Up @@ -64,7 +64,12 @@ async def handle_sign_in_up_api(
user_context=user_context,
)

provider = provider_response.provider
if provider_response is None:
raise BadInputError(
f"the provider {third_party_id} could not be found in the configuration"
)

provider = provider_response

result = await api_implementation.sign_in_up_post(
provider=provider,
Expand Down
2 changes: 1 addition & 1 deletion supertokens_python/recipe/thirdparty/interfaces.py
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,7 @@ async def get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> GetProviderOkResult:
) -> Optional[Provider]:
pass


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -262,13 +262,11 @@ async def find_and_create_provider_instance(
third_party_id: str,
client_type: Optional[str],
user_context: Dict[str, Any],
) -> Provider:
) -> Optional[Provider]:
for provider_input in providers:
if provider_input.config.third_party_id == third_party_id:
provider_instance = create_provider(provider_input)
await fetch_and_set_config(provider_instance, client_type, user_context)
return provider_instance

raise Exception(
f"the provider {third_party_id} could not be found in the configuration"
)
return None
8 changes: 4 additions & 4 deletions supertokens_python/recipe/thirdparty/recipe_implementation.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@
from supertokens_python.querier import Querier

from .interfaces import (
GetProviderOkResult,
ManuallyCreateOrUpdateUserOkResult,
RecipeInterface,
SignInUpOkResult,
Expand Down Expand Up @@ -189,6 +188,9 @@ async def get_provider(
user_context=user_context,
)

if tenant_config is None:
raise Exception("Tenant not found")

merged_providers = merge_providers_from_core_and_static(
provider_configs_from_core=tenant_config.third_party.providers,
provider_inputs_from_static=self.providers,
Expand All @@ -198,6 +200,4 @@ async def get_provider(
merged_providers, third_party_id, client_type, user_context
)

return GetProviderOkResult(
provider,
)
return provider
Original file line number Diff line number Diff line change
Expand Up @@ -149,7 +149,7 @@ async def thirdparty_get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> ThirdPartyInterfaces.GetProviderOkResult:
) -> Optional[ThirdPartyInterfaces.Provider]:
pass

@abstractmethod
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,7 @@
from typing import TYPE_CHECKING, Any, Dict, List, Union, Callable, Optional

import supertokens_python.recipe.emailpassword.interfaces as EPInterfaces
from supertokens_python.recipe.thirdparty.interfaces import GetProviderOkResult
from supertokens_python.recipe.thirdparty.provider import ProviderInput
from supertokens_python.recipe.thirdparty.provider import ProviderInput, Provider
from supertokens_python.recipe.thirdparty.types import RawUserInfoFromProvider
from supertokens_python.recipe.emailpassword.utils import EmailPasswordConfig

Expand Down Expand Up @@ -276,7 +275,7 @@ async def thirdparty_get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> GetProviderOkResult:
) -> Optional[Provider]:
if self.tp_get_provider is None:
raise Exception("No thirdparty provider configured")

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,11 @@
from typing import Any, Dict, List, Optional, Union

from supertokens_python.recipe.thirdparty.interfaces import (
GetProviderOkResult,
ManuallyCreateOrUpdateUserOkResult,
RecipeInterface,
SignInUpOkResult,
)
from supertokens_python.recipe.thirdparty.provider import Provider
from supertokens_python.recipe.thirdparty.types import RawUserInfoFromProvider, User
from supertokens_python.recipe.thirdpartyemailpassword.interfaces import (
RecipeInterface as ThirdPartyEmailPasswordRecipeInterface,
Expand Down Expand Up @@ -164,7 +164,7 @@ async def get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> GetProviderOkResult:
) -> Optional[Provider]:
return await self.recipe_implementation.thirdparty_get_provider(
third_party_id,
client_type,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -136,7 +136,7 @@ async def thirdparty_get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> ThirdPartyInterfaces.GetProviderOkResult:
) -> Optional[ThirdPartyInterfaces.Provider]:
pass

@abstractmethod
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@

from typing import TYPE_CHECKING, Any, Dict, List, Optional, Union

from supertokens_python.recipe.thirdparty.provider import ProviderInput
from supertokens_python.recipe.thirdparty.provider import ProviderInput, Provider
from supertokens_python.recipe.thirdparty.types import RawUserInfoFromProvider

from ...passwordless.interfaces import (
Expand All @@ -42,7 +42,6 @@
UpdateUserUnknownUserIdError,
)
from ...thirdparty.interfaces import (
GetProviderOkResult,
ManuallyCreateOrUpdateUserOkResult,
SignInUpOkResult,
)
Expand Down Expand Up @@ -296,7 +295,7 @@ async def thirdparty_get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> GetProviderOkResult:
) -> Optional[Provider]:
if self.tp_get_provider is None:
raise Exception("No thirdparty provider configured")
return await self.tp_get_provider(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,14 +16,14 @@
from typing import Any, Dict, List, Optional, Union

from supertokens_python.recipe.thirdparty.interfaces import (
GetProviderOkResult,
ManuallyCreateOrUpdateUserOkResult,
RecipeInterface,
SignInUpOkResult,
)
from supertokens_python.recipe.thirdparty.types import RawUserInfoFromProvider, User

from ..interfaces import RecipeInterface as ThirdPartyPasswordlessRecipeInterface
from ...thirdparty.provider import Provider


class RecipeImplementation(RecipeInterface):
Expand Down Expand Up @@ -138,7 +138,7 @@ async def get_provider(
client_type: Optional[str],
tenant_id: str,
user_context: Dict[str, Any],
) -> GetProviderOkResult:
) -> Optional[Provider]:
return await self.recipe_implementation.thirdparty_get_provider(
third_party_id, client_type, tenant_id, user_context
)
Loading