summaryrefslogtreecommitdiff
path: root/tests
diff options
context:
space:
mode:
authorAdrian Holovaty <adrian@holovaty.com>2007-09-15 21:42:51 +0000
committerAdrian Holovaty <adrian@holovaty.com>2007-09-15 21:42:51 +0000
commit5ce2e6c2c827cf877f73bf0e42e6afb7e6a71ccf (patch)
tree8c8c2fb8329e2db7dbfcf2c47026a11ff079e5c5 /tests
parentea9cd5421382c047e2cc140bd6736b54ba660793 (diff)
queryset-refactor: Merged to [6220]
git-svn-id: http://code.djangoproject.com/svn/django/branches/queryset-refactor@6337 bcc190cf-cafb-0310-a4f2-bffc1f526a37
Diffstat (limited to 'tests')
-rw-r--r--tests/modeltests/custom_pk/models.py5
-rw-r--r--tests/modeltests/test_client/models.py16
-rw-r--r--tests/modeltests/test_client/urls.py1
-rw-r--r--tests/modeltests/test_client/views.py8
-rw-r--r--tests/regressiontests/backends/__init__.py0
-rw-r--r--tests/regressiontests/backends/models.py29
-rw-r--r--tests/regressiontests/forms/localflavor.py376
7 files changed, 435 insertions, 0 deletions
diff --git a/tests/modeltests/custom_pk/models.py b/tests/modeltests/custom_pk/models.py
index 53bbadbfd4..375859c897 100644
--- a/tests/modeltests/custom_pk/models.py
+++ b/tests/modeltests/custom_pk/models.py
@@ -1,3 +1,4 @@
+# -*- coding: utf-8 -*-
"""
14. Using a custom primary key
@@ -92,4 +93,8 @@ DoesNotExist: Employee matching query does not exist.
>>> Business.objects.filter(employees__first_name__startswith='Fran')
[<Business: Sears>]
+# Primary key may be unicode string
+>>> emp = Employee(employee_code='jaźń')
+>>> emp.save()
+
"""}
diff --git a/tests/modeltests/test_client/models.py b/tests/modeltests/test_client/models.py
index 32647552eb..2df5d3cf77 100644
--- a/tests/modeltests/test_client/models.py
+++ b/tests/modeltests/test_client/models.py
@@ -250,6 +250,22 @@ class ClientTest(TestCase):
self.assertEqual(response.status_code, 200)
self.assertEqual(response.context['user'].username, 'testclient')
+ def test_view_with_login_and_custom_redirect(self):
+ "Request a page that is protected with @login_required(redirect_field_name='redirect_to')"
+
+ # Get the page without logging in. Should result in 302.
+ response = self.client.get('/test_client/login_protected_view_custom_redirect/')
+ self.assertRedirects(response, 'http://testserver/accounts/login/?redirect_to=/test_client/login_protected_view_custom_redirect/')
+
+ # Log in
+ login = self.client.login(username='testclient', password='password')
+ self.failUnless(login, 'Could not log in')
+
+ # Request a page that requires a login
+ response = self.client.get('/test_client/login_protected_view_custom_redirect/')
+ self.assertEqual(response.status_code, 200)
+ self.assertEqual(response.context['user'].username, 'testclient')
+
def test_view_with_bad_login(self):
"Request a page that is protected with @login, but use bad credentials"
diff --git a/tests/modeltests/test_client/urls.py b/tests/modeltests/test_client/urls.py
index 538c0e4b43..3779a0ecd1 100644
--- a/tests/modeltests/test_client/urls.py
+++ b/tests/modeltests/test_client/urls.py
@@ -13,6 +13,7 @@ urlpatterns = patterns('',
(r'^form_view/$', views.form_view),
(r'^form_view_with_template/$', views.form_view_with_template),
(r'^login_protected_view/$', views.login_protected_view),
+ (r'^login_protected_view_custom_redirect/$', views.login_protected_view_changed_redirect),
(r'^session_view/$', views.session_view),
(r'^broken_view/$', views.broken_view),
(r'^mail_sending_view/$', views.mail_sending_view),
diff --git a/tests/modeltests/test_client/views.py b/tests/modeltests/test_client/views.py
index e2a9081fb2..c406e17d30 100644
--- a/tests/modeltests/test_client/views.py
+++ b/tests/modeltests/test_client/views.py
@@ -122,6 +122,14 @@ def login_protected_view(request):
return HttpResponse(t.render(c))
login_protected_view = login_required(login_protected_view)
+def login_protected_view_changed_redirect(request):
+ "A simple view that is login protected with a custom redirect field set"
+ t = Template('This is a login protected test. Username is {{ user.username }}.', name='Login Template')
+ c = Context({'user': request.user})
+
+ return HttpResponse(t.render(c))
+login_protected_view_changed_redirect = login_required(redirect_field_name="redirect_to")(login_protected_view_changed_redirect)
+
def session_view(request):
"A view that modifies the session"
request.session['tobacconist'] = 'hovercraft'
diff --git a/tests/regressiontests/backends/__init__.py b/tests/regressiontests/backends/__init__.py
new file mode 100644
index 0000000000..e69de29bb2
--- /dev/null
+++ b/tests/regressiontests/backends/__init__.py
diff --git a/tests/regressiontests/backends/models.py b/tests/regressiontests/backends/models.py
new file mode 100644
index 0000000000..50a628a22e
--- /dev/null
+++ b/tests/regressiontests/backends/models.py
@@ -0,0 +1,29 @@
+from django.db import models
+
+class Square(models.Model):
+ root = models.IntegerField()
+ square = models.PositiveIntegerField()
+
+ def __unicode__(self):
+ return "%s ** 2 == %s" % (self.root, self.square)
+
+__test__ = {'API_TESTS': """
+
+#4896: Test cursor.executemany
+>>> from django.db import connection
+>>> cursor = connection.cursor()
+>>> cursor.executemany('INSERT INTO BACKENDS_SQUARE (ROOT, SQUARE) VALUES (%s, %s)',
+... [(i, i**2) for i in range(-5, 6)]) and None or None
+>>> Square.objects.order_by('root')
+[<Square: -5 ** 2 == 25>, <Square: -4 ** 2 == 16>, <Square: -3 ** 2 == 9>, <Square: -2 ** 2 == 4>, <Square: -1 ** 2 == 1>, <Square: 0 ** 2 == 0>, <Square: 1 ** 2 == 1>, <Square: 2 ** 2 == 4>, <Square: 3 ** 2 == 9>, <Square: 4 ** 2 == 16>, <Square: 5 ** 2 == 25>]
+
+#4765: executemany with params=None or params=[] does nothing
+>>> cursor.executemany('INSERT INTO BACKENDS_SQUARE (ROOT, SQUARE) VALUES (%s, %s)', None) and None or None
+>>> Square.objects.count()
+11
+
+>>> cursor.executemany('INSERT INTO BACKENDS_SQUARE (ROOT, SQUARE) VALUES (%s, %s)', []) and None or None
+>>> Square.objects.count()
+11
+
+"""}
diff --git a/tests/regressiontests/forms/localflavor.py b/tests/regressiontests/forms/localflavor.py
index 1d46adfc0b..2fe15847c7 100644
--- a/tests/regressiontests/forms/localflavor.py
+++ b/tests/regressiontests/forms/localflavor.py
@@ -1818,4 +1818,380 @@ u''
u''
>>> f.clean(u'')
u''
+
+# CAPostalCodeField ##############################################################
+
+CAPostalCodeField validates that the data is a six-character Canadian postal code.
+>>> from django.contrib.localflavor.ca.forms import CAPostalCodeField
+>>> f = CAPostalCodeField()
+>>> f.clean('T2S 2H7')
+u'T2S 2H7'
+>>> f.clean('T2S 2H')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean('2T6 H8I')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean('T2S2H')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean(90210)
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean(None)
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+>>> f.clean('')
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+>>> f = CAPostalCodeField(required=False)
+>>> f.clean('T2S 2H7')
+u'T2S 2H7'
+>>> f.clean('T2S2H7')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean('T2S 2H')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean('2T6 H8I')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean('T2S2H')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean(90210)
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a postal code in the format XXX XXX.']
+>>> f.clean(None)
+u''
+>>> f.clean('')
+u''
+
+# CAPhoneNumberField ##########################################################
+
+CAPhoneNumberField validates that the data is a valid Canadian phone number,
+including the area code. It's normalized to XXX-XXX-XXXX format.
+Note: This test is exactly the same as the USPhoneNumberField except using a real
+Candian area code
+
+>>> from django.contrib.localflavor.ca.forms import CAPhoneNumberField
+>>> f = CAPhoneNumberField()
+>>> f.clean('403-555-1212')
+u'403-555-1212'
+>>> f.clean('4035551212')
+u'403-555-1212'
+>>> f.clean('403 555-1212')
+u'403-555-1212'
+>>> f.clean('(403) 555-1212')
+u'403-555-1212'
+>>> f.clean('403 555 1212')
+u'403-555-1212'
+>>> f.clean('403.555.1212')
+u'403-555-1212'
+>>> f.clean('403.555-1212')
+u'403-555-1212'
+>>> f.clean(' (403) 555.1212 ')
+u'403-555-1212'
+>>> f.clean('555-1212')
+Traceback (most recent call last):
+...
+ValidationError: [u'Phone numbers must be in XXX-XXX-XXXX format.']
+>>> f.clean('403-55-1212')
+Traceback (most recent call last):
+...
+ValidationError: [u'Phone numbers must be in XXX-XXX-XXXX format.']
+>>> f.clean(None)
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+>>> f.clean('')
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+
+>>> f = CAPhoneNumberField(required=False)
+>>> f.clean('403-555-1212')
+u'403-555-1212'
+>>> f.clean('4035551212')
+u'403-555-1212'
+>>> f.clean('403 555-1212')
+u'403-555-1212'
+>>> f.clean('(403) 555-1212')
+u'403-555-1212'
+>>> f.clean('403 555 1212')
+u'403-555-1212'
+>>> f.clean('403.555.1212')
+u'403-555-1212'
+>>> f.clean('403.555-1212')
+u'403-555-1212'
+>>> f.clean(' (403) 555.1212 ')
+u'403-555-1212'
+>>> f.clean('555-1212')
+Traceback (most recent call last):
+...
+ValidationError: [u'Phone numbers must be in XXX-XXX-XXXX format.']
+>>> f.clean('403-55-1212')
+Traceback (most recent call last):
+...
+ValidationError: [u'Phone numbers must be in XXX-XXX-XXXX format.']
+>>> f.clean(None)
+u''
+>>> f.clean('')
+u''
+
+# CAProvinceField ################################################################
+
+CAProvinceField validates that the data is either an abbreviation or name of a
+Canadian province.
+>>> from django.contrib.localflavor.ca.forms import CAProvinceField
+>>> f = CAProvinceField()
+>>> f.clean('ab')
+u'AB'
+>>> f.clean('BC')
+u'BC'
+>>> f.clean('nova scotia')
+u'NS'
+>>> f.clean(' manitoba ')
+u'MB'
+>>> f.clean('T2S 2H7')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a Canadian province or territory.']
+>>> f.clean(None)
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+>>> f.clean('')
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+
+>>> f = CAProvinceField(required=False)
+>>> f.clean('ab')
+u'AB'
+>>> f.clean('BC')
+u'BC'
+>>> f.clean('nova scotia')
+u'NS'
+>>> f.clean(' manitoba ')
+u'MB'
+>>> f.clean('T2S 2H7')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a Canadian province or territory.']
+>>> f.clean(None)
+u''
+>>> f.clean('')
+u''
+
+# CAProvinceSelect ###############################################################
+
+CAProvinceSelect is a Select widget that uses a list of Canadian provinces/territories
+as its choices.
+>>> from django.contrib.localflavor.ca.forms import CAProvinceSelect
+>>> w = CAProvinceSelect()
+>>> print w.render('province', 'AB')
+<select name="province">
+<option value="AB" selected="selected">Alberta</option>
+<option value="BC">British Columbia</option>
+<option value="MB">Manitoba</option>
+<option value="NB">New Brunswick</option>
+<option value="NF">Newfoundland and Labrador</option>
+<option value="NT">Northwest Territories</option>
+<option value="NS">Nova Scotia</option>
+<option value="NU">Nunavut</option>
+<option value="ON">Ontario</option>
+<option value="PE">Prince Edward Island</option>
+<option value="QC">Quebec</option>
+<option value="SK">Saskatchewan</option>
+<option value="YK">Yukon</option>
+</select>
+
+# CASocialInsuranceNumberField #################################################
+>>> from django.contrib.localflavor.ca.forms import CASocialInsuranceNumberField
+>>> f = CASocialInsuranceNumberField()
+>>> f.clean('046-454-286')
+u'046-454-286'
+>>> f.clean('046-454-287')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid Canadian Social Insurance number in XXX-XXX-XXXX format.']
+>>> f.clean('046 454 286')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid Canadian Social Insurance number in XXX-XXX-XXXX format.']
+>>> f.clean('046-44-286')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid Canadian Social Insurance number in XXX-XXX-XXXX format.']
+
+## Generic DateField ##########################################################
+
+>>> from django.contrib.localflavor.generic.forms import *
+
+A DateField that uses generic dd/mm/yy dates instead of mm/dd/yy where
+appropriate.
+
+>>> import datetime
+>>> f = DateField()
+>>> f.clean(datetime.date(2006, 10, 25))
+datetime.date(2006, 10, 25)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30))
+datetime.date(2006, 10, 25)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30, 59))
+datetime.date(2006, 10, 25)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30, 59, 200))
+datetime.date(2006, 10, 25)
+>>> f.clean('2006-10-25')
+datetime.date(2006, 10, 25)
+>>> f.clean('25/10/2006')
+datetime.date(2006, 10, 25)
+>>> f.clean('25/10/06')
+datetime.date(2006, 10, 25)
+>>> f.clean('Oct 25 2006')
+datetime.date(2006, 10, 25)
+>>> f.clean('October 25 2006')
+datetime.date(2006, 10, 25)
+>>> f.clean('October 25, 2006')
+datetime.date(2006, 10, 25)
+>>> f.clean('25 October 2006')
+datetime.date(2006, 10, 25)
+>>> f.clean('25 October, 2006')
+datetime.date(2006, 10, 25)
+>>> f.clean('2006-4-31')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date.']
+>>> f.clean('200a-10-25')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date.']
+>>> f.clean('10/25/06')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date.']
+>>> f.clean(None)
+Traceback (most recent call last):
+...
+ValidationError: [u'This field is required.']
+
+>>> f = DateField(required=False)
+>>> f.clean(None)
+>>> repr(f.clean(None))
+'None'
+>>> f.clean('')
+>>> repr(f.clean(''))
+'None'
+
+DateField accepts an optional input_formats parameter:
+>>> f = DateField(input_formats=['%Y %m %d'])
+>>> f.clean(datetime.date(2006, 10, 25))
+datetime.date(2006, 10, 25)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30))
+datetime.date(2006, 10, 25)
+>>> f.clean('2006 10 25')
+datetime.date(2006, 10, 25)
+
+The input_formats parameter overrides all default input formats,
+so the default formats won't work unless you specify them:
+>>> f.clean('2006-10-25')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date.']
+>>> f.clean('25/10/2006')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date.']
+>>> f.clean('25/10/06')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date.']
+
+## Generic DateTimeField ######################################################
+
+A DateField that uses generic dd/mm/yy dates instead of mm/dd/yy where
+appropriate.
+
+>>> import datetime
+>>> f = DateTimeField()
+>>> f.clean(datetime.date(2006, 10, 25))
+datetime.datetime(2006, 10, 25, 0, 0)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30))
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30, 59))
+datetime.datetime(2006, 10, 25, 14, 30, 59)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30, 59, 200))
+datetime.datetime(2006, 10, 25, 14, 30, 59, 200)
+>>> f.clean('2006-10-25 14:30:45')
+datetime.datetime(2006, 10, 25, 14, 30, 45)
+>>> f.clean('2006-10-25 14:30:00')
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean('2006-10-25 14:30')
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean('2006-10-25')
+datetime.datetime(2006, 10, 25, 0, 0)
+>>> f.clean('25/10/2006 14:30:45')
+datetime.datetime(2006, 10, 25, 14, 30, 45)
+>>> f.clean('25/10/2006 14:30:00')
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean('25/10/2006 14:30')
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean('25/10/2006')
+datetime.datetime(2006, 10, 25, 0, 0)
+>>> f.clean('25/10/06 14:30:45')
+datetime.datetime(2006, 10, 25, 14, 30, 45)
+>>> f.clean('25/10/06 14:30:00')
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean('25/10/06 14:30')
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean('25/10/06')
+datetime.datetime(2006, 10, 25, 0, 0)
+>>> f.clean('hello')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date/time.']
+>>> f.clean('2006-10-25 4:30 p.m.')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date/time.']
+
+DateField accepts an optional input_formats parameter:
+>>> f = DateTimeField(input_formats=['%Y %m %d %I:%M %p'])
+>>> f.clean(datetime.date(2006, 10, 25))
+datetime.datetime(2006, 10, 25, 0, 0)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30))
+datetime.datetime(2006, 10, 25, 14, 30)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30, 59))
+datetime.datetime(2006, 10, 25, 14, 30, 59)
+>>> f.clean(datetime.datetime(2006, 10, 25, 14, 30, 59, 200))
+datetime.datetime(2006, 10, 25, 14, 30, 59, 200)
+>>> f.clean('2006 10 25 2:30 PM')
+datetime.datetime(2006, 10, 25, 14, 30)
+
+The input_formats parameter overrides all default input formats,
+so the default formats won't work unless you specify them:
+>>> f.clean('2006-10-25 14:30:45')
+Traceback (most recent call last):
+...
+ValidationError: [u'Enter a valid date/time.']
+
+>>> f = DateTimeField(required=False)
+>>> f.clean(None)
+>>> repr(f.clean(None))
+'None'
+>>> f.clean('')
+>>> repr(f.clean(''))
+'None'
+
"""