Accessing the request.user object when testing Django
Asked Answered
C

2

6

I'm trying to access the request.user object when testing my app using django's client class.

from django.test import TestCase
from django.test.client import Client

class SomeTestCase(TestCase):

    def setUp(self):
        self.client = Client()
        self.client.login( username="foo", password="bar")

    def test_one(self):
        response = self.client.get("/my_profile/")
        self.fail( response.request.user )

This will obviously fail, but it fails because response.request doesn't have a user attribute.

AttributeError: 'dict' object has no attribute 'user'

Is there any way to access the user object from the client instance? I want to do this in order to check if some test user's data is properly rendered. I can try to tackle this by setting up all the necessary info during setUp, but before I do that I wanted to check if I'm not just missing something.

Carrel answered 25/2, 2012 at 21:2 Comment(0)
L
2

Use response.context['user'].

User is automatically available in the template context if you use RequestContext. See auth data in templates doc.

Otherwise i believe you should just query it:

 def test_one(self):
    response = self.client.get("/my_profile/")
    user = User.objects.get(username="foo")
    self.fail( user.some_field == False )
Leukocyte answered 25/2, 2012 at 22:13 Comment(1)
See #2840967 this uses Secator's recommendation but in the setUp and tearDown methods, just a bit cleaner.Swift
R
3

This may seem a roundabout way of doing it but it can be useful.

Use RequestFactory, its pretty straightforward. It imitates the request object.

from django.test import TestCase, RequestFactory 
from django.test.client import Client
from django.contrib.auth.models import User

class SomeTestCase(TestCase):

    def setUp(self):
        self.client = Client()
        self.factory = RequestFactory()
        self.user = User.objects.create_user(
                    username='foo', email='foo@bar', 
                    password='bar')

    def test_one(self):
        self.client.login( username="foo", password="bar")

        request = self.factory.get("/my_profile/")
        request.user = self.user

        #rest of your code

    def tearDown(self):
        self.user.delete()

I hope that was helpful.

Rhineland answered 1/3, 2018 at 15:49 Comment(0)
L
2

Use response.context['user'].

User is automatically available in the template context if you use RequestContext. See auth data in templates doc.

Otherwise i believe you should just query it:

 def test_one(self):
    response = self.client.get("/my_profile/")
    user = User.objects.get(username="foo")
    self.fail( user.some_field == False )
Leukocyte answered 25/2, 2012 at 22:13 Comment(1)
See #2840967 this uses Secator's recommendation but in the setUp and tearDown methods, just a bit cleaner.Swift

© 2022 - 2024 — McMap. All rights reserved.