jazzband / django-oauth-toolkit

OAuth2 goodies for the Djangonauts!
https://django-oauth-toolkit.readthedocs.io
Other
3.13k stars 792 forks source link

django-oauth-toolkit request object don`t have custom attribute added by middleware #897

Open vinayinfo opened 3 years ago

vinayinfo commented 3 years ago

Describe the bug https://stackoverflow.com/questions/64862642/django-oauth-toolkit-request-object-dont-have-custom-attribute-added-by-middlew

To Reproduce I have created a middleware and added my_name attribute in request and accessing this in custom authentication class but getting attribute error.

class MyMainMiddleware(MiddlewareMixin):

    def process_request(self, request):
        request.my_name = "my name"

added middleware MyMainMiddleware in settings

MIDDLEWARE = [
    "apps.middleware.MyMainMiddleware",
    "django.middleware.security.SecurityMiddleware",
    'corsheaders.middleware.CorsMiddleware',
    "django.contrib.sessions.middleware.SessionMiddleware",
    "oauth2_provider.middleware.OAuth2TokenMiddleware",
    "django.middleware.common.CommonMiddleware",
    "django.middleware.csrf.CsrfViewMiddleware",
    "django.contrib.auth.middleware.AuthenticationMiddleware",
    "django.contrib.messages.middleware.MessageMiddleware",
    "django.middleware.clickjacking.XFrameOptionsMiddleware",
]
AUTHENTICATION_BACKENDS = [
    "apps.accounts.backends.ModelBackend",
]

views.py

from oauth2_provider.oauth2_validators import OAuth2Validator
from django.contrib.auth import authenticate
class OAuth2Validator(OAuth2Validator):
    def validate_user(self, username, password, client, request, *args, **kwargs):
        """
        Check username and password correspond to a valid and active User
        """
        u = authenticate(request, username=username, password=password)
        if u is not None and u.is_active:
            request.user = u
            return True
        return False

class CustomTokenView(TokenView):
    validator_class = OAuth2Validator

    @method_decorator(sensitive_post_parameters("password"))
    def post(self, request, *args, **kwargs):
        return super(CustomTokenView, self).post(request, *args, **kwargs)

curl request for token

curl -X POST \
  http://localhost:8000/authenticate/token/ \
  -F grant_type=password \
  -F username=<user> \
  -F password=<password> \
  -F client_id=<client_id> \
  -F client_secret=<client_secret>

Below is the traceback

  File "/usr/local/lib/python3.7/site-packages/oauthlib/oauth2/rfc6749/grant_types/resource_owner_password_credentials.py", line 184, in validate_token_request
    request.password, request.client, request):
  File "/code/apps/accounts/views.py", line 39, in validate_user
    u = authenticate(request, username=username, password=password)
  File "/usr/local/lib/python3.7/site-packages/django/contrib/auth/__init__.py", line 73, in authenticate
    user = backend.authenticate(request, **credentials)
  File "/code/apps/accounts/backends.py", line 16, in authenticate
    if username is None:
  File "/usr/local/lib/python3.7/site-packages/oauthlib/common.py", line 436, in __getattr__
    raise AttributeError(name)
AttributeError: my_name

Can someone please look into this. I am unable to get any request attributed which is set by middleware.

Expected behavior

Version

Additional context

MattBlack85 commented 3 years ago

@vinaynfo do you mind preparing a test case? that would be the best init to tackle this problem