iMerica / dj-rest-auth

Authentication for Django Rest Framework
https://dj-rest-auth.readthedocs.io/en/latest/index.html
MIT License
1.63k stars 304 forks source link

String indices must be integers (Google Login) #516

Open kmemonahmed opened 1 year ago

kmemonahmed commented 1 year ago

When trying log in with google with Django version 4.1.5 and Python 3.10 it Always gives this error,

Housain-maina commented 1 year ago

The reason why this is happening is because the 'complete_login' method in 'GoogleOAuth2Adapter' class is trying to access 'response["id_token"]' and the key does not exist. But since 'response' returns only the value of 'id_token' you can create a custom 'GoogleOAuth2Adapter' by modify it the following way:

from allauth.socialaccount.providers.oauth2.client import OAuth2Client, OAuth2Error
from dj_rest_auth.registration.views import SocialLoginView
from allauth.socialaccount.providers.google.provider import GoogleProvider
from allauth.socialaccount.providers.google import views as google_views
from allauth.socialaccount.providers.oauth2.views import OAuth2Adapter
import jwt

class GoogleOAuth2Adapter(OAuth2Adapter):
    provider_id = GoogleProvider.id
    access_token_url = google_views.ACCESS_TOKEN_URL
    authorize_url = google_views.AUTHORIZE_URL
    id_token_issuer = google_views.ID_TOKEN_ISSUER

    def complete_login(self, request, app, token, response, **kwargs):
            try:
                identity_data = jwt.decode(
-               response["id_token"],       # removed line
+               response,                   # added line
                    # Since the token was received by direct communication
                    # protected by TLS between this library and Google, we
                    # are allowed to skip checking the token signature
                    # according to the OpenID Connect Core 1.0
                    # specification.
                    # https://openid.net/specs/openid-connect-core-1_0.html#IDTokenValidation
                    options={
                        "verify_signature": False,
                        "verify_iss": True,
                        "verify_aud": True,
                        "verify_exp": True,
                    },
                    issuer=self.id_token_issuer,
                    audience=app.client_id,
                )
            except jwt.PyJWTError as e:
                raise OAuth2Error("Invalid id_token") from e
            login = self.get_provider().sociallogin_from_response(request, identity_data)
            return login

then

class GoogleLogin(SocialLoginView):
    adapter_class = GoogleOAuth2Adapter
    client_class = OAuth2Client

I'll create a PR for this fix.

kmemonahmed commented 1 year ago

Good, please let me know when the PR will be merged, it will help me to close this issue and also using in my project.