summaryrefslogtreecommitdiff
path: root/django/contrib/auth
diff options
context:
space:
mode:
authorArthur Koziel <arthur@arthurkoziel.com>2010-09-13 00:04:27 +0000
committerArthur Koziel <arthur@arthurkoziel.com>2010-09-13 00:04:27 +0000
commitdd49269c7db008b2567f50cb03c4d3d9b321daa1 (patch)
tree326dd25bb045ac016cda7966b43cbdfe1f67d699 /django/contrib/auth
parentc9b188c4ec939abbe48dae5a371276742e64b6b8 (diff)
downloaddjango-soc2010/app-loading.tar.gz
[soc2010/app-loading] merged trunkarchive/soc2010/app-loadingsoc2010/app-loading
git-svn-id: http://code.djangoproject.com/svn/django/branches/soc2010/app-loading@13818 bcc190cf-cafb-0310-a4f2-bffc1f526a37
Diffstat (limited to 'django/contrib/auth')
-rw-r--r--django/contrib/auth/decorators.py3
-rw-r--r--django/contrib/auth/forms.py10
-rw-r--r--django/contrib/auth/tests/__init__.py3
-rw-r--r--django/contrib/auth/tests/decorators.py30
-rw-r--r--django/contrib/auth/tests/forms.py483
-rw-r--r--django/contrib/auth/tests/urls.py5
-rw-r--r--django/contrib/auth/tests/views.py37
-rw-r--r--django/contrib/auth/views.py3
8 files changed, 313 insertions, 261 deletions
diff --git a/django/contrib/auth/decorators.py b/django/contrib/auth/decorators.py
index 09dcf42e42..7d7a0cddb7 100644
--- a/django/contrib/auth/decorators.py
+++ b/django/contrib/auth/decorators.py
@@ -30,13 +30,14 @@ def user_passes_test(test_func, login_url=None, redirect_field_name=REDIRECT_FIE
return decorator
-def login_required(function=None, redirect_field_name=REDIRECT_FIELD_NAME):
+def login_required(function=None, redirect_field_name=REDIRECT_FIELD_NAME, login_url=None):
"""
Decorator for views that checks that the user is logged in, redirecting
to the log-in page if necessary.
"""
actual_decorator = user_passes_test(
lambda u: u.is_authenticated(),
+ login_url=login_url,
redirect_field_name=redirect_field_name
)
if function:
diff --git a/django/contrib/auth/forms.py b/django/contrib/auth/forms.py
index 086acf3349..cc0f7071c3 100644
--- a/django/contrib/auth/forms.py
+++ b/django/contrib/auth/forms.py
@@ -52,6 +52,12 @@ class UserChangeForm(forms.ModelForm):
class Meta:
model = User
+ def __init__(self, *args, **kwargs):
+ super(UserChangeForm, self).__init__(*args, **kwargs)
+ f = self.fields.get('user_permissions', None)
+ if f is not None:
+ f.queryset = f.queryset.select_related('content_type')
+
class AuthenticationForm(forms.Form):
"""
Base class for authenticating users. Extend this to get a form that accepts
@@ -111,7 +117,7 @@ class PasswordResetForm(forms.Form):
return email
def save(self, domain_override=None, email_template_name='registration/password_reset_email.html',
- use_https=False, token_generator=default_token_generator):
+ use_https=False, token_generator=default_token_generator, from_email=None):
"""
Generates a one-use only link for resetting password and sends to the user
"""
@@ -134,7 +140,7 @@ class PasswordResetForm(forms.Form):
'protocol': use_https and 'https' or 'http',
}
send_mail(_("Password reset on %s") % site_name,
- t.render(Context(c)), None, [user.email])
+ t.render(Context(c)), from_email, [user.email])
class SetPasswordForm(forms.Form):
"""
diff --git a/django/contrib/auth/tests/__init__.py b/django/contrib/auth/tests/__init__.py
index 965ea2d6be..a1d02b6014 100644
--- a/django/contrib/auth/tests/__init__.py
+++ b/django/contrib/auth/tests/__init__.py
@@ -1,7 +1,7 @@
from django.contrib.auth.tests.auth_backends import BackendTest, RowlevelBackendTest, AnonymousUserBackendTest, NoAnonymousUserBackendTest
from django.contrib.auth.tests.basic import BASIC_TESTS
from django.contrib.auth.tests.decorators import LoginRequiredTestCase
-from django.contrib.auth.tests.forms import FORM_TESTS
+from django.contrib.auth.tests.forms import UserCreationFormTest, AuthenticationFormTest, SetPasswordFormTest, PasswordChangeFormTest, UserChangeFormTest, PasswordResetFormTest
from django.contrib.auth.tests.remote_user \
import RemoteUserTest, RemoteUserNoCreateTest, RemoteUserCustomTest
from django.contrib.auth.tests.models import ProfileTestCase
@@ -13,6 +13,5 @@ from django.contrib.auth.tests.views \
__test__ = {
'BASIC_TESTS': BASIC_TESTS,
- 'FORM_TESTS': FORM_TESTS,
'TOKEN_GENERATOR_TESTS': TOKEN_GENERATOR_TESTS,
}
diff --git a/django/contrib/auth/tests/decorators.py b/django/contrib/auth/tests/decorators.py
index 7efd9d8ccf..0240a76eb7 100644
--- a/django/contrib/auth/tests/decorators.py
+++ b/django/contrib/auth/tests/decorators.py
@@ -1,12 +1,12 @@
-from unittest import TestCase
-
from django.contrib.auth.decorators import login_required
+from django.contrib.auth.tests.views import AuthViewsTestCase
-
-class LoginRequiredTestCase(TestCase):
+class LoginRequiredTestCase(AuthViewsTestCase):
"""
Tests the login_required decorators
"""
+ urls = 'django.contrib.auth.tests.urls'
+
def testCallable(self):
"""
Check that login_required is assignable to callable objects.
@@ -22,4 +22,24 @@ class LoginRequiredTestCase(TestCase):
"""
def normal_view(request):
pass
- login_required(normal_view) \ No newline at end of file
+ login_required(normal_view)
+
+ def testLoginRequired(self, view_url='/login_required/', login_url='/login/'):
+ """
+ Check that login_required works on a simple view wrapped in a
+ login_required decorator.
+ """
+ response = self.client.get(view_url)
+ self.assertEqual(response.status_code, 302)
+ self.assert_(login_url in response['Location'])
+ self.login()
+ response = self.client.get(view_url)
+ self.assertEqual(response.status_code, 200)
+
+ def testLoginRequiredNextUrl(self):
+ """
+ Check that login_required works on a simple view wrapped in a
+ login_required decorator with a login_url set.
+ """
+ self.testLoginRequired(view_url='/login_required_login_url/',
+ login_url='/somewhere/') \ No newline at end of file
diff --git a/django/contrib/auth/tests/forms.py b/django/contrib/auth/tests/forms.py
index b691c560be..5aa49e09c3 100644
--- a/django/contrib/auth/tests/forms.py
+++ b/django/contrib/auth/tests/forms.py
@@ -1,231 +1,252 @@
-
-FORM_TESTS = """
->>> from django.contrib.auth.models import User
->>> from django.contrib.auth.forms import UserCreationForm, AuthenticationForm
->>> from django.contrib.auth.forms import PasswordChangeForm, SetPasswordForm
-
-# The user already exists.
-
->>> user = User.objects.create_user("jsmith", "jsmith@example.com", "test123")
->>> data = {
-... 'username': 'jsmith',
-... 'password1': 'test123',
-... 'password2': 'test123',
-... }
->>> form = UserCreationForm(data)
->>> form.is_valid()
-False
->>> form["username"].errors
-[u'A user with that username already exists.']
-
-# The username contains invalid data.
-
->>> data = {
-... 'username': 'jsmith!',
-... 'password1': 'test123',
-... 'password2': 'test123',
-... }
->>> form = UserCreationForm(data)
->>> form.is_valid()
-False
->>> form["username"].errors
-[u'This value may contain only letters, numbers and @/./+/-/_ characters.']
-
-# The verification password is incorrect.
-
->>> data = {
-... 'username': 'jsmith2',
-... 'password1': 'test123',
-... 'password2': 'test',
-... }
->>> form = UserCreationForm(data)
->>> form.is_valid()
-False
->>> form["password2"].errors
-[u"The two password fields didn't match."]
-
-# One (or both) passwords weren't given
-
->>> data = {'username': 'jsmith2'}
->>> form = UserCreationForm(data)
->>> form.is_valid()
-False
->>> form['password1'].errors
-[u'This field is required.']
->>> form['password2'].errors
-[u'This field is required.']
-
->>> data['password2'] = 'test123'
->>> form = UserCreationForm(data)
->>> form.is_valid()
-False
->>> form['password1'].errors
-[u'This field is required.']
-
-# The success case.
-
->>> data = {
-... 'username': 'jsmith2@example.com',
-... 'password1': 'test123',
-... 'password2': 'test123',
-... }
->>> form = UserCreationForm(data)
->>> form.is_valid()
-True
->>> form.save()
-<User: jsmith2@example.com>
-
-# The user submits an invalid username.
-
->>> data = {
-... 'username': 'jsmith_does_not_exist',
-... 'password': 'test123',
-... }
-
->>> form = AuthenticationForm(None, data)
->>> form.is_valid()
-False
->>> form.non_field_errors()
-[u'Please enter a correct username and password. Note that both fields are case-sensitive.']
-
-# The user is inactive.
-
->>> data = {
-... 'username': 'jsmith',
-... 'password': 'test123',
-... }
->>> user.is_active = False
->>> user.save()
->>> form = AuthenticationForm(None, data)
->>> form.is_valid()
-False
->>> form.non_field_errors()
-[u'This account is inactive.']
-
->>> user.is_active = True
->>> user.save()
-
-# The success case
-
->>> form = AuthenticationForm(None, data)
->>> form.is_valid()
-True
->>> form.non_field_errors()
-[]
-
-### SetPasswordForm:
-
-# The two new passwords do not match.
-
->>> data = {
-... 'new_password1': 'abc123',
-... 'new_password2': 'abc',
-... }
->>> form = SetPasswordForm(user, data)
->>> form.is_valid()
-False
->>> form["new_password2"].errors
-[u"The two password fields didn't match."]
-
-# The success case.
-
->>> data = {
-... 'new_password1': 'abc123',
-... 'new_password2': 'abc123',
-... }
->>> form = SetPasswordForm(user, data)
->>> form.is_valid()
-True
-
-### PasswordChangeForm:
-
-The old password is incorrect.
-
->>> data = {
-... 'old_password': 'test',
-... 'new_password1': 'abc123',
-... 'new_password2': 'abc123',
-... }
->>> form = PasswordChangeForm(user, data)
->>> form.is_valid()
-False
->>> form["old_password"].errors
-[u'Your old password was entered incorrectly. Please enter it again.']
-
-# The two new passwords do not match.
-
->>> data = {
-... 'old_password': 'test123',
-... 'new_password1': 'abc123',
-... 'new_password2': 'abc',
-... }
->>> form = PasswordChangeForm(user, data)
->>> form.is_valid()
-False
->>> form["new_password2"].errors
-[u"The two password fields didn't match."]
-
-# The success case.
-
->>> data = {
-... 'old_password': 'test123',
-... 'new_password1': 'abc123',
-... 'new_password2': 'abc123',
-... }
->>> form = PasswordChangeForm(user, data)
->>> form.is_valid()
-True
-
-# Regression test - check the order of fields:
-
->>> PasswordChangeForm(user, {}).fields.keys()
-['old_password', 'new_password1', 'new_password2']
-
-### UserChangeForm
-
->>> from django.contrib.auth.forms import UserChangeForm
->>> data = {'username': 'not valid'}
->>> form = UserChangeForm(data, instance=user)
->>> form.is_valid()
-False
->>> form['username'].errors
-[u'This value may contain only letters, numbers and @/./+/-/_ characters.']
-
-
-### PasswordResetForm
-
->>> from django.contrib.auth.forms import PasswordResetForm
->>> data = {'email':'not valid'}
->>> form = PasswordResetForm(data)
->>> form.is_valid()
-False
->>> form['email'].errors
-[u'Enter a valid e-mail address.']
-
-# Test nonexistant email address
->>> data = {'email':'foo@bar.com'}
->>> form = PasswordResetForm(data)
->>> form.is_valid()
-False
->>> form.errors
-{'email': [u"That e-mail address doesn't have an associated user account. Are you sure you've registered?"]}
-
-# Test cleaned_data bug fix
->>> user = User.objects.create_user("jsmith3", "jsmith3@example.com", "test123")
->>> data = {'email':'jsmith3@example.com'}
->>> form = PasswordResetForm(data)
->>> form.is_valid()
-True
->>> form.cleaned_data['email']
-u'jsmith3@example.com'
-
-# bug #5605, preserve the case of the user name (before the @ in the email address)
-# when creating a user.
->>> user = User.objects.create_user('forms_test2', 'tesT@EXAMple.com', 'test')
->>> user.email
-'tesT@example.com'
->>> user = User.objects.create_user('forms_test3', 'tesT', 'test')
->>> user.email
-'tesT'
-
-"""
+from django.contrib.auth.models import User
+from django.contrib.auth.forms import UserCreationForm, AuthenticationForm, PasswordChangeForm, SetPasswordForm, UserChangeForm, PasswordResetForm
+from django.test import TestCase
+
+
+class UserCreationFormTest(TestCase):
+
+ fixtures = ['authtestdata.json']
+
+ def test_user_already_exists(self):
+ data = {
+ 'username': 'testclient',
+ 'password1': 'test123',
+ 'password2': 'test123',
+ }
+ form = UserCreationForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form["username"].errors,
+ [u'A user with that username already exists.'])
+
+ def test_invalid_data(self):
+ data = {
+ 'username': 'jsmith!',
+ 'password1': 'test123',
+ 'password2': 'test123',
+ }
+ form = UserCreationForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form["username"].errors,
+ [u'This value may contain only letters, numbers and @/./+/-/_ characters.'])
+
+
+ def test_password_verification(self):
+ # The verification password is incorrect.
+ data = {
+ 'username': 'jsmith',
+ 'password1': 'test123',
+ 'password2': 'test',
+ }
+ form = UserCreationForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form["password2"].errors,
+ [u"The two password fields didn't match."])
+
+
+ def test_both_passwords(self):
+ # One (or both) passwords weren't given
+ data = {'username': 'jsmith'}
+ form = UserCreationForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form['password1'].errors,
+ [u'This field is required.'])
+ self.assertEqual(form['password2'].errors,
+ [u'This field is required.'])
+
+
+ data['password2'] = 'test123'
+ form = UserCreationForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form['password1'].errors,
+ [u'This field is required.'])
+
+ def test_success(self):
+ # The success case.
+
+ data = {
+ 'username': 'jsmith@example.com',
+ 'password1': 'test123',
+ 'password2': 'test123',
+ }
+ form = UserCreationForm(data)
+ self.assertTrue(form.is_valid())
+ u = form.save()
+ self.assertEqual(repr(u), '<User: jsmith@example.com>')
+
+
+class AuthenticationFormTest(TestCase):
+
+ fixtures = ['authtestdata.json']
+
+ def test_invalid_username(self):
+ # The user submits an invalid username.
+
+ data = {
+ 'username': 'jsmith_does_not_exist',
+ 'password': 'test123',
+ }
+ form = AuthenticationForm(None, data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form.non_field_errors(),
+ [u'Please enter a correct username and password. Note that both fields are case-sensitive.'])
+
+ def test_inactive_user(self):
+ # The user is inactive.
+ data = {
+ 'username': 'inactive',
+ 'password': 'password',
+ }
+ form = AuthenticationForm(None, data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form.non_field_errors(),
+ [u'This account is inactive.'])
+
+
+ def test_success(self):
+ # The success case
+ data = {
+ 'username': 'testclient',
+ 'password': 'password',
+ }
+ form = AuthenticationForm(None, data)
+ self.assertTrue(form.is_valid())
+ self.assertEqual(form.non_field_errors(), [])
+
+
+class SetPasswordFormTest(TestCase):
+
+ fixtures = ['authtestdata.json']
+
+ def test_password_verification(self):
+ # The two new passwords do not match.
+ user = User.objects.get(username='testclient')
+ data = {
+ 'new_password1': 'abc123',
+ 'new_password2': 'abc',
+ }
+ form = SetPasswordForm(user, data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form["new_password2"].errors,
+ [u"The two password fields didn't match."])
+
+ def test_success(self):
+ user = User.objects.get(username='testclient')
+ data = {
+ 'new_password1': 'abc123',
+ 'new_password2': 'abc123',
+ }
+ form = SetPasswordForm(user, data)
+ self.assertTrue(form.is_valid())
+
+
+class PasswordChangeFormTest(TestCase):
+
+ fixtures = ['authtestdata.json']
+
+ def test_incorrect_password(self):
+ user = User.objects.get(username='testclient')
+ data = {
+ 'old_password': 'test',
+ 'new_password1': 'abc123',
+ 'new_password2': 'abc123',
+ }
+ form = PasswordChangeForm(user, data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form["old_password"].errors,
+ [u'Your old password was entered incorrectly. Please enter it again.'])
+
+
+ def test_password_verification(self):
+ # The two new passwords do not match.
+ user = User.objects.get(username='testclient')
+ data = {
+ 'old_password': 'password',
+ 'new_password1': 'abc123',
+ 'new_password2': 'abc',
+ }
+ form = PasswordChangeForm(user, data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form["new_password2"].errors,
+ [u"The two password fields didn't match."])
+
+
+ def test_success(self):
+ # The success case.
+ user = User.objects.get(username='testclient')
+ data = {
+ 'old_password': 'password',
+ 'new_password1': 'abc123',
+ 'new_password2': 'abc123',
+ }
+ form = PasswordChangeForm(user, data)
+ self.assertTrue(form.is_valid())
+
+ def test_field_order(self):
+ # Regression test - check the order of fields:
+ user = User.objects.get(username='testclient')
+ self.assertEqual(PasswordChangeForm(user, {}).fields.keys(),
+ ['old_password', 'new_password1', 'new_password2'])
+
+class UserChangeFormTest(TestCase):
+
+ fixtures = ['authtestdata.json']
+
+ def test_username_validity(self):
+ user = User.objects.get(username='testclient')
+ data = {'username': 'not valid'}
+ form = UserChangeForm(data, instance=user)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form['username'].errors,
+ [u'This value may contain only letters, numbers and @/./+/-/_ characters.'])
+
+ def test_bug_14242(self):
+ # A regression test, introduce by adding an optimization for the
+ # UserChangeForm.
+
+ class MyUserForm(UserChangeForm):
+ def __init__(self, *args, **kwargs):
+ super(MyUserForm, self).__init__(*args, **kwargs)
+ self.fields['groups'].help_text = 'These groups give users different permissions'
+
+ class Meta(UserChangeForm.Meta):
+ fields = ('groups',)
+
+ # Just check we can create it
+ form = MyUserForm({})
+
+
+class PasswordResetFormTest(TestCase):
+
+ fixtures = ['authtestdata.json']
+
+ def test_invalid_email(self):
+ data = {'email':'not valid'}
+ form = PasswordResetForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form['email'].errors,
+ [u'Enter a valid e-mail address.'])
+
+ def test_nonexistant_email(self):
+ # Test nonexistant email address
+ data = {'email':'foo@bar.com'}
+ form = PasswordResetForm(data)
+ self.assertFalse(form.is_valid())
+ self.assertEqual(form.errors,
+ {'email': [u"That e-mail address doesn't have an associated user account. Are you sure you've registered?"]})
+
+ def test_cleaned_data(self):
+ # Regression test
+ user = User.objects.create_user("jsmith3", "jsmith3@example.com", "test123")
+ data = {'email':'jsmith3@example.com'}
+ form = PasswordResetForm(data)
+ self.assertTrue(form.is_valid())
+ self.assertEqual(form.cleaned_data['email'], u'jsmith3@example.com')
+
+
+ def test_bug_5605(self):
+ # bug #5605, preserve the case of the user name (before the @ in the
+ # email address) when creating a user.
+ user = User.objects.create_user('forms_test2', 'tesT@EXAMple.com', 'test')
+ self.assertEqual(user.email, 'tesT@example.com')
+ user = User.objects.create_user('forms_test3', 'tesT', 'test')
+ self.assertEqual(user.email, 'tesT')
diff --git a/django/contrib/auth/tests/urls.py b/django/contrib/auth/tests/urls.py
index f94b8daa7f..bc2f7e705f 100644
--- a/django/contrib/auth/tests/urls.py
+++ b/django/contrib/auth/tests/urls.py
@@ -1,5 +1,7 @@
from django.conf.urls.defaults import patterns
from django.contrib.auth.urls import urlpatterns
+from django.contrib.auth.views import password_reset
+from django.contrib.auth.decorators import login_required
from django.http import HttpResponse
from django.template import Template, RequestContext
@@ -14,5 +16,8 @@ urlpatterns += patterns('',
(r'^logout/custom_query/$', 'django.contrib.auth.views.logout', dict(redirect_field_name='follow')),
(r'^logout/next_page/$', 'django.contrib.auth.views.logout', dict(next_page='/somewhere/')),
(r'^remote_user/$', remote_user_auth_view),
+ (r'^password_reset_from_email/$', 'django.contrib.auth.views.password_reset', dict(from_email='staffmember@example.com')),
+ (r'^login_required/$', login_required(password_reset)),
+ (r'^login_required_login_url/$', login_required(password_reset, login_url='/somewhere/')),
)
diff --git a/django/contrib/auth/tests/views.py b/django/contrib/auth/tests/views.py
index d894e6dafd..e20afbc5b0 100644
--- a/django/contrib/auth/tests/views.py
+++ b/django/contrib/auth/tests/views.py
@@ -36,6 +36,16 @@ class AuthViewsTestCase(TestCase):
settings.LANGUAGE_CODE = self.old_LANGUAGE_CODE
settings.TEMPLATE_DIRS = self.old_TEMPLATE_DIRS
+ def login(self, password='password'):
+ response = self.client.post('/login/', {
+ 'username': 'testclient',
+ 'password': password
+ }
+ )
+ self.assertEquals(response.status_code, 302)
+ self.assert_(response['Location'].endswith(settings.LOGIN_REDIRECT_URL))
+ self.assert_(SESSION_KEY in self.client.session)
+
class PasswordResetTest(AuthViewsTestCase):
def test_email_not_found(self):
@@ -52,6 +62,14 @@ class PasswordResetTest(AuthViewsTestCase):
self.assertEquals(response.status_code, 302)
self.assertEquals(len(mail.outbox), 1)
self.assert_("http://" in mail.outbox[0].body)
+ self.assertEquals(settings.DEFAULT_FROM_EMAIL, mail.outbox[0].from_email)
+
+ def test_email_found_custom_from(self):
+ "Email is sent if a valid email address is provided for password reset when a custom from_email is provided."
+ response = self.client.post('/password_reset_from_email/', {'email': 'staffmember@example.com'})
+ self.assertEquals(response.status_code, 302)
+ self.assertEquals(len(mail.outbox), 1)
+ self.assertEquals("staffmember@example.com", mail.outbox[0].from_email)
def _test_confirm_start(self):
# Start by creating the email
@@ -118,15 +136,6 @@ class PasswordResetTest(AuthViewsTestCase):
class ChangePasswordTest(AuthViewsTestCase):
- def login(self, password='password'):
- response = self.client.post('/login/', {
- 'username': 'testclient',
- 'password': password
- }
- )
- self.assertEquals(response.status_code, 302)
- self.assert_(response['Location'].endswith(settings.LOGIN_REDIRECT_URL))
-
def fail_login(self, password='password'):
response = self.client.post('/login/', {
'username': 'testclient',
@@ -228,16 +237,6 @@ class LoginTest(AuthViewsTestCase):
class LogoutTest(AuthViewsTestCase):
urls = 'django.contrib.auth.tests.urls'
- def login(self, password='password'):
- response = self.client.post('/login/', {
- 'username': 'testclient',
- 'password': password
- }
- )
- self.assertEquals(response.status_code, 302)
- self.assert_(response['Location'].endswith(settings.LOGIN_REDIRECT_URL))
- self.assert_(SESSION_KEY in self.client.session)
-
def confirm_logged_out(self):
self.assert_(SESSION_KEY not in self.client.session)
diff --git a/django/contrib/auth/views.py b/django/contrib/auth/views.py
index b2e875a869..eaa0dbeba2 100644
--- a/django/contrib/auth/views.py
+++ b/django/contrib/auth/views.py
@@ -105,7 +105,7 @@ def redirect_to_login(next, login_url=None, redirect_field_name=REDIRECT_FIELD_N
def password_reset(request, is_admin_site=False, template_name='registration/password_reset_form.html',
email_template_name='registration/password_reset_email.html',
password_reset_form=PasswordResetForm, token_generator=default_token_generator,
- post_reset_redirect=None):
+ post_reset_redirect=None, from_email=None):
if post_reset_redirect is None:
post_reset_redirect = reverse('django.contrib.auth.views.password_reset_done')
if request.method == "POST":
@@ -114,6 +114,7 @@ def password_reset(request, is_admin_site=False, template_name='registration/pas
opts = {}
opts['use_https'] = request.is_secure()
opts['token_generator'] = token_generator
+ opts['from_email'] = from_email
if is_admin_site:
opts['domain_override'] = request.META['HTTP_HOST']
else: