Implemented auto-escaping of variable output in templates. Fully controllable by...
[django.git] / tests / regressiontests / forms / forms.py
blob7c0cf8abf3c662391d91966b31f6a715fa5b61ae
1 # -*- coding: utf-8 -*-
2 tests = r"""
3 >>> from django.newforms import *
4 >>> import datetime
5 >>> import time
6 >>> import re
7 >>> try:
8 ... from decimal import Decimal
9 ... except ImportError:
10 ... from django.utils._decimal import Decimal
12 #########
13 # Forms #
14 #########
16 A Form is a collection of Fields. It knows how to validate a set of data and it
17 knows how to render itself in a couple of default ways (e.g., an HTML table).
18 You can pass it data in __init__(), as a dictionary.
20 # Form ########################################################################
22 >>> class Person(Form):
23 ... first_name = CharField()
24 ... last_name = CharField()
25 ... birthday = DateField()
27 Pass a dictionary to a Form's __init__().
28 >>> p = Person({'first_name': u'John', 'last_name': u'Lennon', 'birthday': u'1940-10-9'})
29 >>> p.is_bound
30 True
31 >>> p.errors
33 >>> p.is_valid()
34 True
35 >>> p.errors.as_ul()
36 u''
37 >>> p.errors.as_text()
38 u''
39 >>> p.cleaned_data
40 {'first_name': u'John', 'last_name': u'Lennon', 'birthday': datetime.date(1940, 10, 9)}
41 >>> print p['first_name']
42 <input type="text" name="first_name" value="John" id="id_first_name" />
43 >>> print p['last_name']
44 <input type="text" name="last_name" value="Lennon" id="id_last_name" />
45 >>> print p['birthday']
46 <input type="text" name="birthday" value="1940-10-9" id="id_birthday" />
47 >>> print p['nonexistentfield']
48 Traceback (most recent call last):
49 ...
50 KeyError: "Key 'nonexistentfield' not found in Form"
52 >>> for boundfield in p:
53 ... print boundfield
54 <input type="text" name="first_name" value="John" id="id_first_name" />
55 <input type="text" name="last_name" value="Lennon" id="id_last_name" />
56 <input type="text" name="birthday" value="1940-10-9" id="id_birthday" />
57 >>> for boundfield in p:
58 ... print boundfield.label, boundfield.data
59 First name John
60 Last name Lennon
61 Birthday 1940-10-9
62 >>> print p
63 <tr><th><label for="id_first_name">First name:</label></th><td><input type="text" name="first_name" value="John" id="id_first_name" /></td></tr>
64 <tr><th><label for="id_last_name">Last name:</label></th><td><input type="text" name="last_name" value="Lennon" id="id_last_name" /></td></tr>
65 <tr><th><label for="id_birthday">Birthday:</label></th><td><input type="text" name="birthday" value="1940-10-9" id="id_birthday" /></td></tr>
67 Empty dictionaries are valid, too.
68 >>> p = Person({})
69 >>> p.is_bound
70 True
71 >>> p.errors
72 {'first_name': [u'This field is required.'], 'last_name': [u'This field is required.'], 'birthday': [u'This field is required.']}
73 >>> p.is_valid()
74 False
75 >>> p.cleaned_data
76 Traceback (most recent call last):
77 ...
78 AttributeError: 'Person' object has no attribute 'cleaned_data'
79 >>> print p
80 <tr><th><label for="id_first_name">First name:</label></th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="first_name" id="id_first_name" /></td></tr>
81 <tr><th><label for="id_last_name">Last name:</label></th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="last_name" id="id_last_name" /></td></tr>
82 <tr><th><label for="id_birthday">Birthday:</label></th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="birthday" id="id_birthday" /></td></tr>
83 >>> print p.as_table()
84 <tr><th><label for="id_first_name">First name:</label></th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="first_name" id="id_first_name" /></td></tr>
85 <tr><th><label for="id_last_name">Last name:</label></th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="last_name" id="id_last_name" /></td></tr>
86 <tr><th><label for="id_birthday">Birthday:</label></th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="birthday" id="id_birthday" /></td></tr>
87 >>> print p.as_ul()
88 <li><ul class="errorlist"><li>This field is required.</li></ul><label for="id_first_name">First name:</label> <input type="text" name="first_name" id="id_first_name" /></li>
89 <li><ul class="errorlist"><li>This field is required.</li></ul><label for="id_last_name">Last name:</label> <input type="text" name="last_name" id="id_last_name" /></li>
90 <li><ul class="errorlist"><li>This field is required.</li></ul><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" id="id_birthday" /></li>
91 >>> print p.as_p()
92 <ul class="errorlist"><li>This field is required.</li></ul>
93 <p><label for="id_first_name">First name:</label> <input type="text" name="first_name" id="id_first_name" /></p>
94 <ul class="errorlist"><li>This field is required.</li></ul>
95 <p><label for="id_last_name">Last name:</label> <input type="text" name="last_name" id="id_last_name" /></p>
96 <ul class="errorlist"><li>This field is required.</li></ul>
97 <p><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" id="id_birthday" /></p>
99 If you don't pass any values to the Form's __init__(), or if you pass None,
100 the Form will be considered unbound and won't do any validation. Form.errors
101 will be an empty dictionary *but* Form.is_valid() will return False.
102 >>> p = Person()
103 >>> p.is_bound
104 False
105 >>> p.errors
107 >>> p.is_valid()
108 False
109 >>> p.cleaned_data
110 Traceback (most recent call last):
112 AttributeError: 'Person' object has no attribute 'cleaned_data'
113 >>> print p
114 <tr><th><label for="id_first_name">First name:</label></th><td><input type="text" name="first_name" id="id_first_name" /></td></tr>
115 <tr><th><label for="id_last_name">Last name:</label></th><td><input type="text" name="last_name" id="id_last_name" /></td></tr>
116 <tr><th><label for="id_birthday">Birthday:</label></th><td><input type="text" name="birthday" id="id_birthday" /></td></tr>
117 >>> print p.as_table()
118 <tr><th><label for="id_first_name">First name:</label></th><td><input type="text" name="first_name" id="id_first_name" /></td></tr>
119 <tr><th><label for="id_last_name">Last name:</label></th><td><input type="text" name="last_name" id="id_last_name" /></td></tr>
120 <tr><th><label for="id_birthday">Birthday:</label></th><td><input type="text" name="birthday" id="id_birthday" /></td></tr>
121 >>> print p.as_ul()
122 <li><label for="id_first_name">First name:</label> <input type="text" name="first_name" id="id_first_name" /></li>
123 <li><label for="id_last_name">Last name:</label> <input type="text" name="last_name" id="id_last_name" /></li>
124 <li><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" id="id_birthday" /></li>
125 >>> print p.as_p()
126 <p><label for="id_first_name">First name:</label> <input type="text" name="first_name" id="id_first_name" /></p>
127 <p><label for="id_last_name">Last name:</label> <input type="text" name="last_name" id="id_last_name" /></p>
128 <p><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" id="id_birthday" /></p>
130 Unicode values are handled properly.
131 >>> p = Person({'first_name': u'John', 'last_name': u'\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111', 'birthday': '1940-10-9'})
132 >>> p.as_table()
133 u'<tr><th><label for="id_first_name">First name:</label></th><td><input type="text" name="first_name" value="John" id="id_first_name" /></td></tr>\n<tr><th><label for="id_last_name">Last name:</label></th><td><input type="text" name="last_name" value="\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111" id="id_last_name" /></td></tr>\n<tr><th><label for="id_birthday">Birthday:</label></th><td><input type="text" name="birthday" value="1940-10-9" id="id_birthday" /></td></tr>'
134 >>> p.as_ul()
135 u'<li><label for="id_first_name">First name:</label> <input type="text" name="first_name" value="John" id="id_first_name" /></li>\n<li><label for="id_last_name">Last name:</label> <input type="text" name="last_name" value="\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111" id="id_last_name" /></li>\n<li><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" value="1940-10-9" id="id_birthday" /></li>'
136 >>> p.as_p()
137 u'<p><label for="id_first_name">First name:</label> <input type="text" name="first_name" value="John" id="id_first_name" /></p>\n<p><label for="id_last_name">Last name:</label> <input type="text" name="last_name" value="\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111" id="id_last_name" /></p>\n<p><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" value="1940-10-9" id="id_birthday" /></p>'
139 >>> p = Person({'last_name': u'Lennon'})
140 >>> p.errors
141 {'first_name': [u'This field is required.'], 'birthday': [u'This field is required.']}
142 >>> p.is_valid()
143 False
144 >>> p.errors.as_ul()
145 u'<ul class="errorlist"><li>first_name<ul class="errorlist"><li>This field is required.</li></ul></li><li>birthday<ul class="errorlist"><li>This field is required.</li></ul></li></ul>'
146 >>> print p.errors.as_text()
147 * first_name
148 * This field is required.
149 * birthday
150 * This field is required.
151 >>> p.cleaned_data
152 Traceback (most recent call last):
154 AttributeError: 'Person' object has no attribute 'cleaned_data'
155 >>> p['first_name'].errors
156 [u'This field is required.']
157 >>> p['first_name'].errors.as_ul()
158 u'<ul class="errorlist"><li>This field is required.</li></ul>'
159 >>> p['first_name'].errors.as_text()
160 u'* This field is required.'
162 >>> p = Person()
163 >>> print p['first_name']
164 <input type="text" name="first_name" id="id_first_name" />
165 >>> print p['last_name']
166 <input type="text" name="last_name" id="id_last_name" />
167 >>> print p['birthday']
168 <input type="text" name="birthday" id="id_birthday" />
170 cleaned_data will always *only* contain a key for fields defined in the
171 Form, even if you pass extra data when you define the Form. In this
172 example, we pass a bunch of extra fields to the form constructor,
173 but cleaned_data contains only the form's fields.
174 >>> data = {'first_name': u'John', 'last_name': u'Lennon', 'birthday': u'1940-10-9', 'extra1': 'hello', 'extra2': 'hello'}
175 >>> p = Person(data)
176 >>> p.is_valid()
177 True
178 >>> p.cleaned_data
179 {'first_name': u'John', 'last_name': u'Lennon', 'birthday': datetime.date(1940, 10, 9)}
181 cleaned_data will include a key and value for *all* fields defined in the Form,
182 even if the Form's data didn't include a value for fields that are not
183 required. In this example, the data dictionary doesn't include a value for the
184 "nick_name" field, but cleaned_data includes it. For CharFields, it's set to the
185 empty string.
186 >>> class OptionalPersonForm(Form):
187 ... first_name = CharField()
188 ... last_name = CharField()
189 ... nick_name = CharField(required=False)
190 >>> data = {'first_name': u'John', 'last_name': u'Lennon'}
191 >>> f = OptionalPersonForm(data)
192 >>> f.is_valid()
193 True
194 >>> f.cleaned_data
195 {'nick_name': u'', 'first_name': u'John', 'last_name': u'Lennon'}
197 For DateFields, it's set to None.
198 >>> class OptionalPersonForm(Form):
199 ... first_name = CharField()
200 ... last_name = CharField()
201 ... birth_date = DateField(required=False)
202 >>> data = {'first_name': u'John', 'last_name': u'Lennon'}
203 >>> f = OptionalPersonForm(data)
204 >>> f.is_valid()
205 True
206 >>> f.cleaned_data
207 {'birth_date': None, 'first_name': u'John', 'last_name': u'Lennon'}
209 "auto_id" tells the Form to add an "id" attribute to each form element.
210 If it's a string that contains '%s', Django will use that as a format string
211 into which the field's name will be inserted. It will also put a <label> around
212 the human-readable labels for a field.
213 >>> p = Person(auto_id='%s_id')
214 >>> print p.as_table()
215 <tr><th><label for="first_name_id">First name:</label></th><td><input type="text" name="first_name" id="first_name_id" /></td></tr>
216 <tr><th><label for="last_name_id">Last name:</label></th><td><input type="text" name="last_name" id="last_name_id" /></td></tr>
217 <tr><th><label for="birthday_id">Birthday:</label></th><td><input type="text" name="birthday" id="birthday_id" /></td></tr>
218 >>> print p.as_ul()
219 <li><label for="first_name_id">First name:</label> <input type="text" name="first_name" id="first_name_id" /></li>
220 <li><label for="last_name_id">Last name:</label> <input type="text" name="last_name" id="last_name_id" /></li>
221 <li><label for="birthday_id">Birthday:</label> <input type="text" name="birthday" id="birthday_id" /></li>
222 >>> print p.as_p()
223 <p><label for="first_name_id">First name:</label> <input type="text" name="first_name" id="first_name_id" /></p>
224 <p><label for="last_name_id">Last name:</label> <input type="text" name="last_name" id="last_name_id" /></p>
225 <p><label for="birthday_id">Birthday:</label> <input type="text" name="birthday" id="birthday_id" /></p>
227 If auto_id is any True value whose str() does not contain '%s', the "id"
228 attribute will be the name of the field.
229 >>> p = Person(auto_id=True)
230 >>> print p.as_ul()
231 <li><label for="first_name">First name:</label> <input type="text" name="first_name" id="first_name" /></li>
232 <li><label for="last_name">Last name:</label> <input type="text" name="last_name" id="last_name" /></li>
233 <li><label for="birthday">Birthday:</label> <input type="text" name="birthday" id="birthday" /></li>
235 If auto_id is any False value, an "id" attribute won't be output unless it
236 was manually entered.
237 >>> p = Person(auto_id=False)
238 >>> print p.as_ul()
239 <li>First name: <input type="text" name="first_name" /></li>
240 <li>Last name: <input type="text" name="last_name" /></li>
241 <li>Birthday: <input type="text" name="birthday" /></li>
243 In this example, auto_id is False, but the "id" attribute for the "first_name"
244 field is given. Also note that field gets a <label>, while the others don't.
245 >>> class PersonNew(Form):
246 ... first_name = CharField(widget=TextInput(attrs={'id': 'first_name_id'}))
247 ... last_name = CharField()
248 ... birthday = DateField()
249 >>> p = PersonNew(auto_id=False)
250 >>> print p.as_ul()
251 <li><label for="first_name_id">First name:</label> <input type="text" id="first_name_id" name="first_name" /></li>
252 <li>Last name: <input type="text" name="last_name" /></li>
253 <li>Birthday: <input type="text" name="birthday" /></li>
255 If the "id" attribute is specified in the Form and auto_id is True, the "id"
256 attribute in the Form gets precedence.
257 >>> p = PersonNew(auto_id=True)
258 >>> print p.as_ul()
259 <li><label for="first_name_id">First name:</label> <input type="text" id="first_name_id" name="first_name" /></li>
260 <li><label for="last_name">Last name:</label> <input type="text" name="last_name" id="last_name" /></li>
261 <li><label for="birthday">Birthday:</label> <input type="text" name="birthday" id="birthday" /></li>
263 >>> class SignupForm(Form):
264 ... email = EmailField()
265 ... get_spam = BooleanField()
266 >>> f = SignupForm(auto_id=False)
267 >>> print f['email']
268 <input type="text" name="email" />
269 >>> print f['get_spam']
270 <input type="checkbox" name="get_spam" />
272 >>> f = SignupForm({'email': 'test@example.com', 'get_spam': True}, auto_id=False)
273 >>> print f['email']
274 <input type="text" name="email" value="test@example.com" />
275 >>> print f['get_spam']
276 <input checked="checked" type="checkbox" name="get_spam" />
278 Any Field can have a Widget class passed to its constructor:
279 >>> class ContactForm(Form):
280 ... subject = CharField()
281 ... message = CharField(widget=Textarea)
282 >>> f = ContactForm(auto_id=False)
283 >>> print f['subject']
284 <input type="text" name="subject" />
285 >>> print f['message']
286 <textarea rows="10" cols="40" name="message"></textarea>
288 as_textarea(), as_text() and as_hidden() are shortcuts for changing the output
289 widget type:
290 >>> f['subject'].as_textarea()
291 u'<textarea rows="10" cols="40" name="subject"></textarea>'
292 >>> f['message'].as_text()
293 u'<input type="text" name="message" />'
294 >>> f['message'].as_hidden()
295 u'<input type="hidden" name="message" />'
297 The 'widget' parameter to a Field can also be an instance:
298 >>> class ContactForm(Form):
299 ... subject = CharField()
300 ... message = CharField(widget=Textarea(attrs={'rows': 80, 'cols': 20}))
301 >>> f = ContactForm(auto_id=False)
302 >>> print f['message']
303 <textarea rows="80" cols="20" name="message"></textarea>
305 Instance-level attrs are *not* carried over to as_textarea(), as_text() and
306 as_hidden():
307 >>> f['message'].as_text()
308 u'<input type="text" name="message" />'
309 >>> f = ContactForm({'subject': 'Hello', 'message': 'I love you.'}, auto_id=False)
310 >>> f['subject'].as_textarea()
311 u'<textarea rows="10" cols="40" name="subject">Hello</textarea>'
312 >>> f['message'].as_text()
313 u'<input type="text" name="message" value="I love you." />'
314 >>> f['message'].as_hidden()
315 u'<input type="hidden" name="message" value="I love you." />'
317 For a form with a <select>, use ChoiceField:
318 >>> class FrameworkForm(Form):
319 ... name = CharField()
320 ... language = ChoiceField(choices=[('P', 'Python'), ('J', 'Java')])
321 >>> f = FrameworkForm(auto_id=False)
322 >>> print f['language']
323 <select name="language">
324 <option value="P">Python</option>
325 <option value="J">Java</option>
326 </select>
327 >>> f = FrameworkForm({'name': 'Django', 'language': 'P'}, auto_id=False)
328 >>> print f['language']
329 <select name="language">
330 <option value="P" selected="selected">Python</option>
331 <option value="J">Java</option>
332 </select>
334 A subtlety: If one of the choices' value is the empty string and the form is
335 unbound, then the <option> for the empty-string choice will get selected="selected".
336 >>> class FrameworkForm(Form):
337 ... name = CharField()
338 ... language = ChoiceField(choices=[('', '------'), ('P', 'Python'), ('J', 'Java')])
339 >>> f = FrameworkForm(auto_id=False)
340 >>> print f['language']
341 <select name="language">
342 <option value="" selected="selected">------</option>
343 <option value="P">Python</option>
344 <option value="J">Java</option>
345 </select>
347 You can specify widget attributes in the Widget constructor.
348 >>> class FrameworkForm(Form):
349 ... name = CharField()
350 ... language = ChoiceField(choices=[('P', 'Python'), ('J', 'Java')], widget=Select(attrs={'class': 'foo'}))
351 >>> f = FrameworkForm(auto_id=False)
352 >>> print f['language']
353 <select class="foo" name="language">
354 <option value="P">Python</option>
355 <option value="J">Java</option>
356 </select>
357 >>> f = FrameworkForm({'name': 'Django', 'language': 'P'}, auto_id=False)
358 >>> print f['language']
359 <select class="foo" name="language">
360 <option value="P" selected="selected">Python</option>
361 <option value="J">Java</option>
362 </select>
364 When passing a custom widget instance to ChoiceField, note that setting
365 'choices' on the widget is meaningless. The widget will use the choices
366 defined on the Field, not the ones defined on the Widget.
367 >>> class FrameworkForm(Form):
368 ... name = CharField()
369 ... language = ChoiceField(choices=[('P', 'Python'), ('J', 'Java')], widget=Select(choices=[('R', 'Ruby'), ('P', 'Perl')], attrs={'class': 'foo'}))
370 >>> f = FrameworkForm(auto_id=False)
371 >>> print f['language']
372 <select class="foo" name="language">
373 <option value="P">Python</option>
374 <option value="J">Java</option>
375 </select>
376 >>> f = FrameworkForm({'name': 'Django', 'language': 'P'}, auto_id=False)
377 >>> print f['language']
378 <select class="foo" name="language">
379 <option value="P" selected="selected">Python</option>
380 <option value="J">Java</option>
381 </select>
383 You can set a ChoiceField's choices after the fact.
384 >>> class FrameworkForm(Form):
385 ... name = CharField()
386 ... language = ChoiceField()
387 >>> f = FrameworkForm(auto_id=False)
388 >>> print f['language']
389 <select name="language">
390 </select>
391 >>> f.fields['language'].choices = [('P', 'Python'), ('J', 'Java')]
392 >>> print f['language']
393 <select name="language">
394 <option value="P">Python</option>
395 <option value="J">Java</option>
396 </select>
398 Add widget=RadioSelect to use that widget with a ChoiceField.
399 >>> class FrameworkForm(Form):
400 ... name = CharField()
401 ... language = ChoiceField(choices=[('P', 'Python'), ('J', 'Java')], widget=RadioSelect)
402 >>> f = FrameworkForm(auto_id=False)
403 >>> print f['language']
404 <ul>
405 <li><label><input type="radio" name="language" value="P" /> Python</label></li>
406 <li><label><input type="radio" name="language" value="J" /> Java</label></li>
407 </ul>
408 >>> print f
409 <tr><th>Name:</th><td><input type="text" name="name" /></td></tr>
410 <tr><th>Language:</th><td><ul>
411 <li><label><input type="radio" name="language" value="P" /> Python</label></li>
412 <li><label><input type="radio" name="language" value="J" /> Java</label></li>
413 </ul></td></tr>
414 >>> print f.as_ul()
415 <li>Name: <input type="text" name="name" /></li>
416 <li>Language: <ul>
417 <li><label><input type="radio" name="language" value="P" /> Python</label></li>
418 <li><label><input type="radio" name="language" value="J" /> Java</label></li>
419 </ul></li>
421 Regarding auto_id and <label>, RadioSelect is a special case. Each radio button
422 gets a distinct ID, formed by appending an underscore plus the button's
423 zero-based index.
424 >>> f = FrameworkForm(auto_id='id_%s')
425 >>> print f['language']
426 <ul>
427 <li><label><input type="radio" id="id_language_0" value="P" name="language" /> Python</label></li>
428 <li><label><input type="radio" id="id_language_1" value="J" name="language" /> Java</label></li>
429 </ul>
431 When RadioSelect is used with auto_id, and the whole form is printed using
432 either as_table() or as_ul(), the label for the RadioSelect will point to the
433 ID of the *first* radio button.
434 >>> print f
435 <tr><th><label for="id_name">Name:</label></th><td><input type="text" name="name" id="id_name" /></td></tr>
436 <tr><th><label for="id_language_0">Language:</label></th><td><ul>
437 <li><label><input type="radio" id="id_language_0" value="P" name="language" /> Python</label></li>
438 <li><label><input type="radio" id="id_language_1" value="J" name="language" /> Java</label></li>
439 </ul></td></tr>
440 >>> print f.as_ul()
441 <li><label for="id_name">Name:</label> <input type="text" name="name" id="id_name" /></li>
442 <li><label for="id_language_0">Language:</label> <ul>
443 <li><label><input type="radio" id="id_language_0" value="P" name="language" /> Python</label></li>
444 <li><label><input type="radio" id="id_language_1" value="J" name="language" /> Java</label></li>
445 </ul></li>
446 >>> print f.as_p()
447 <p><label for="id_name">Name:</label> <input type="text" name="name" id="id_name" /></p>
448 <p><label for="id_language_0">Language:</label> <ul>
449 <li><label><input type="radio" id="id_language_0" value="P" name="language" /> Python</label></li>
450 <li><label><input type="radio" id="id_language_1" value="J" name="language" /> Java</label></li>
451 </ul></p>
453 MultipleChoiceField is a special case, as its data is required to be a list:
454 >>> class SongForm(Form):
455 ... name = CharField()
456 ... composers = MultipleChoiceField()
457 >>> f = SongForm(auto_id=False)
458 >>> print f['composers']
459 <select multiple="multiple" name="composers">
460 </select>
461 >>> class SongForm(Form):
462 ... name = CharField()
463 ... composers = MultipleChoiceField(choices=[('J', 'John Lennon'), ('P', 'Paul McCartney')])
464 >>> f = SongForm(auto_id=False)
465 >>> print f['composers']
466 <select multiple="multiple" name="composers">
467 <option value="J">John Lennon</option>
468 <option value="P">Paul McCartney</option>
469 </select>
470 >>> f = SongForm({'name': 'Yesterday', 'composers': ['P']}, auto_id=False)
471 >>> print f['name']
472 <input type="text" name="name" value="Yesterday" />
473 >>> print f['composers']
474 <select multiple="multiple" name="composers">
475 <option value="J">John Lennon</option>
476 <option value="P" selected="selected">Paul McCartney</option>
477 </select>
479 MultipleChoiceField rendered as_hidden() is a special case. Because it can
480 have multiple values, its as_hidden() renders multiple <input type="hidden">
481 tags.
482 >>> f = SongForm({'name': 'Yesterday', 'composers': ['P']}, auto_id=False)
483 >>> print f['composers'].as_hidden()
484 <input type="hidden" name="composers" value="P" />
485 >>> f = SongForm({'name': 'From Me To You', 'composers': ['P', 'J']}, auto_id=False)
486 >>> print f['composers'].as_hidden()
487 <input type="hidden" name="composers" value="P" />
488 <input type="hidden" name="composers" value="J" />
490 MultipleChoiceField can also be used with the CheckboxSelectMultiple widget.
491 >>> class SongForm(Form):
492 ... name = CharField()
493 ... composers = MultipleChoiceField(choices=[('J', 'John Lennon'), ('P', 'Paul McCartney')], widget=CheckboxSelectMultiple)
494 >>> f = SongForm(auto_id=False)
495 >>> print f['composers']
496 <ul>
497 <li><label><input type="checkbox" name="composers" value="J" /> John Lennon</label></li>
498 <li><label><input type="checkbox" name="composers" value="P" /> Paul McCartney</label></li>
499 </ul>
500 >>> f = SongForm({'composers': ['J']}, auto_id=False)
501 >>> print f['composers']
502 <ul>
503 <li><label><input checked="checked" type="checkbox" name="composers" value="J" /> John Lennon</label></li>
504 <li><label><input type="checkbox" name="composers" value="P" /> Paul McCartney</label></li>
505 </ul>
506 >>> f = SongForm({'composers': ['J', 'P']}, auto_id=False)
507 >>> print f['composers']
508 <ul>
509 <li><label><input checked="checked" type="checkbox" name="composers" value="J" /> John Lennon</label></li>
510 <li><label><input checked="checked" type="checkbox" name="composers" value="P" /> Paul McCartney</label></li>
511 </ul>
513 Regarding auto_id, CheckboxSelectMultiple is a special case. Each checkbox
514 gets a distinct ID, formed by appending an underscore plus the checkbox's
515 zero-based index.
516 >>> f = SongForm(auto_id='%s_id')
517 >>> print f['composers']
518 <ul>
519 <li><label><input type="checkbox" name="composers" value="J" id="composers_id_0" /> John Lennon</label></li>
520 <li><label><input type="checkbox" name="composers" value="P" id="composers_id_1" /> Paul McCartney</label></li>
521 </ul>
523 Data for a MultipleChoiceField should be a list. QueryDict and MultiValueDict
524 conveniently work with this.
525 >>> data = {'name': 'Yesterday', 'composers': ['J', 'P']}
526 >>> f = SongForm(data)
527 >>> f.errors
529 >>> from django.http import QueryDict
530 >>> data = QueryDict('name=Yesterday&composers=J&composers=P')
531 >>> f = SongForm(data)
532 >>> f.errors
534 >>> from django.utils.datastructures import MultiValueDict
535 >>> data = MultiValueDict(dict(name=['Yesterday'], composers=['J', 'P']))
536 >>> f = SongForm(data)
537 >>> f.errors
540 The MultipleHiddenInput widget renders multiple values as hidden fields.
541 >>> class SongFormHidden(Form):
542 ... name = CharField()
543 ... composers = MultipleChoiceField(choices=[('J', 'John Lennon'), ('P', 'Paul McCartney')], widget=MultipleHiddenInput)
544 >>> f = SongFormHidden(MultiValueDict(dict(name=['Yesterday'], composers=['J', 'P'])), auto_id=False)
545 >>> print f.as_ul()
546 <li>Name: <input type="text" name="name" value="Yesterday" /><input type="hidden" name="composers" value="J" />
547 <input type="hidden" name="composers" value="P" /></li>
549 When using CheckboxSelectMultiple, the framework expects a list of input and
550 returns a list of input.
551 >>> f = SongForm({'name': 'Yesterday'}, auto_id=False)
552 >>> f.errors
553 {'composers': [u'This field is required.']}
554 >>> f = SongForm({'name': 'Yesterday', 'composers': ['J']}, auto_id=False)
555 >>> f.errors
557 >>> f.cleaned_data
558 {'composers': [u'J'], 'name': u'Yesterday'}
559 >>> f = SongForm({'name': 'Yesterday', 'composers': ['J', 'P']}, auto_id=False)
560 >>> f.errors
562 >>> f.cleaned_data
563 {'composers': [u'J', u'P'], 'name': u'Yesterday'}
565 Validation errors are HTML-escaped when output as HTML.
566 >>> class EscapingForm(Form):
567 ... special_name = CharField()
568 ... def clean_special_name(self):
569 ... raise ValidationError("Something's wrong with '%s'" % self.cleaned_data['special_name'])
571 >>> f = EscapingForm({'special_name': "Nothing to escape"}, auto_id=False)
572 >>> print f
573 <tr><th>Special name:</th><td><ul class="errorlist"><li>Something&#39;s wrong with &#39;Nothing to escape&#39;</li></ul><input type="text" name="special_name" value="Nothing to escape" /></td></tr>
574 >>> f = EscapingForm({'special_name': "Should escape < & > and <script>alert('xss')</script>"}, auto_id=False)
575 >>> print f
576 <tr><th>Special name:</th><td><ul class="errorlist"><li>Something&#39;s wrong with &#39;Should escape &lt; &amp; &gt; and &lt;script&gt;alert(&#39;xss&#39;)&lt;/script&gt;&#39;</li></ul><input type="text" name="special_name" value="Should escape &lt; &amp; &gt; and &lt;script&gt;alert(&#39;xss&#39;)&lt;/script&gt;" /></td></tr>
578 """ + \
579 r""" # [This concatenation is to keep the string below the jython's 32K limit].
580 # Validating multiple fields in relation to another ###########################
582 There are a couple of ways to do multiple-field validation. If you want the
583 validation message to be associated with a particular field, implement the
584 clean_XXX() method on the Form, where XXX is the field name. As in
585 Field.clean(), the clean_XXX() method should return the cleaned value. In the
586 clean_XXX() method, you have access to self.cleaned_data, which is a dictionary
587 of all the data that has been cleaned *so far*, in order by the fields,
588 including the current field (e.g., the field XXX if you're in clean_XXX()).
589 >>> class UserRegistration(Form):
590 ... username = CharField(max_length=10)
591 ... password1 = CharField(widget=PasswordInput)
592 ... password2 = CharField(widget=PasswordInput)
593 ... def clean_password2(self):
594 ... if self.cleaned_data.get('password1') and self.cleaned_data.get('password2') and self.cleaned_data['password1'] != self.cleaned_data['password2']:
595 ... raise ValidationError(u'Please make sure your passwords match.')
596 ... return self.cleaned_data['password2']
597 >>> f = UserRegistration(auto_id=False)
598 >>> f.errors
600 >>> f = UserRegistration({}, auto_id=False)
601 >>> f.errors
602 {'username': [u'This field is required.'], 'password1': [u'This field is required.'], 'password2': [u'This field is required.']}
603 >>> f = UserRegistration({'username': 'adrian', 'password1': 'foo', 'password2': 'bar'}, auto_id=False)
604 >>> f.errors
605 {'password2': [u'Please make sure your passwords match.']}
606 >>> f = UserRegistration({'username': 'adrian', 'password1': 'foo', 'password2': 'foo'}, auto_id=False)
607 >>> f.errors
609 >>> f.cleaned_data
610 {'username': u'adrian', 'password1': u'foo', 'password2': u'foo'}
612 Another way of doing multiple-field validation is by implementing the
613 Form's clean() method. If you do this, any ValidationError raised by that
614 method will not be associated with a particular field; it will have a
615 special-case association with the field named '__all__'.
616 Note that in Form.clean(), you have access to self.cleaned_data, a dictionary of
617 all the fields/values that have *not* raised a ValidationError. Also note
618 Form.clean() is required to return a dictionary of all clean data.
619 >>> class UserRegistration(Form):
620 ... username = CharField(max_length=10)
621 ... password1 = CharField(widget=PasswordInput)
622 ... password2 = CharField(widget=PasswordInput)
623 ... def clean(self):
624 ... if self.cleaned_data.get('password1') and self.cleaned_data.get('password2') and self.cleaned_data['password1'] != self.cleaned_data['password2']:
625 ... raise ValidationError(u'Please make sure your passwords match.')
626 ... return self.cleaned_data
627 >>> f = UserRegistration(auto_id=False)
628 >>> f.errors
630 >>> f = UserRegistration({}, auto_id=False)
631 >>> print f.as_table()
632 <tr><th>Username:</th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="text" name="username" maxlength="10" /></td></tr>
633 <tr><th>Password1:</th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="password" name="password1" /></td></tr>
634 <tr><th>Password2:</th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="password" name="password2" /></td></tr>
635 >>> f.errors
636 {'username': [u'This field is required.'], 'password1': [u'This field is required.'], 'password2': [u'This field is required.']}
637 >>> f = UserRegistration({'username': 'adrian', 'password1': 'foo', 'password2': 'bar'}, auto_id=False)
638 >>> f.errors
639 {'__all__': [u'Please make sure your passwords match.']}
640 >>> print f.as_table()
641 <tr><td colspan="2"><ul class="errorlist"><li>Please make sure your passwords match.</li></ul></td></tr>
642 <tr><th>Username:</th><td><input type="text" name="username" value="adrian" maxlength="10" /></td></tr>
643 <tr><th>Password1:</th><td><input type="password" name="password1" value="foo" /></td></tr>
644 <tr><th>Password2:</th><td><input type="password" name="password2" value="bar" /></td></tr>
645 >>> print f.as_ul()
646 <li><ul class="errorlist"><li>Please make sure your passwords match.</li></ul></li>
647 <li>Username: <input type="text" name="username" value="adrian" maxlength="10" /></li>
648 <li>Password1: <input type="password" name="password1" value="foo" /></li>
649 <li>Password2: <input type="password" name="password2" value="bar" /></li>
650 >>> f = UserRegistration({'username': 'adrian', 'password1': 'foo', 'password2': 'foo'}, auto_id=False)
651 >>> f.errors
653 >>> f.cleaned_data
654 {'username': u'adrian', 'password1': u'foo', 'password2': u'foo'}
656 # Dynamic construction ########################################################
658 It's possible to construct a Form dynamically by adding to the self.fields
659 dictionary in __init__(). Don't forget to call Form.__init__() within the
660 subclass' __init__().
661 >>> class Person(Form):
662 ... first_name = CharField()
663 ... last_name = CharField()
664 ... def __init__(self, *args, **kwargs):
665 ... super(Person, self).__init__(*args, **kwargs)
666 ... self.fields['birthday'] = DateField()
667 >>> p = Person(auto_id=False)
668 >>> print p
669 <tr><th>First name:</th><td><input type="text" name="first_name" /></td></tr>
670 <tr><th>Last name:</th><td><input type="text" name="last_name" /></td></tr>
671 <tr><th>Birthday:</th><td><input type="text" name="birthday" /></td></tr>
673 Instances of a dynamic Form do not persist fields from one Form instance to
674 the next.
675 >>> class MyForm(Form):
676 ... def __init__(self, data=None, auto_id=False, field_list=[]):
677 ... Form.__init__(self, data, auto_id=auto_id)
678 ... for field in field_list:
679 ... self.fields[field[0]] = field[1]
680 >>> field_list = [('field1', CharField()), ('field2', CharField())]
681 >>> my_form = MyForm(field_list=field_list)
682 >>> print my_form
683 <tr><th>Field1:</th><td><input type="text" name="field1" /></td></tr>
684 <tr><th>Field2:</th><td><input type="text" name="field2" /></td></tr>
685 >>> field_list = [('field3', CharField()), ('field4', CharField())]
686 >>> my_form = MyForm(field_list=field_list)
687 >>> print my_form
688 <tr><th>Field3:</th><td><input type="text" name="field3" /></td></tr>
689 <tr><th>Field4:</th><td><input type="text" name="field4" /></td></tr>
691 >>> class MyForm(Form):
692 ... default_field_1 = CharField()
693 ... default_field_2 = CharField()
694 ... def __init__(self, data=None, auto_id=False, field_list=[]):
695 ... Form.__init__(self, data, auto_id=auto_id)
696 ... for field in field_list:
697 ... self.fields[field[0]] = field[1]
698 >>> field_list = [('field1', CharField()), ('field2', CharField())]
699 >>> my_form = MyForm(field_list=field_list)
700 >>> print my_form
701 <tr><th>Default field 1:</th><td><input type="text" name="default_field_1" /></td></tr>
702 <tr><th>Default field 2:</th><td><input type="text" name="default_field_2" /></td></tr>
703 <tr><th>Field1:</th><td><input type="text" name="field1" /></td></tr>
704 <tr><th>Field2:</th><td><input type="text" name="field2" /></td></tr>
705 >>> field_list = [('field3', CharField()), ('field4', CharField())]
706 >>> my_form = MyForm(field_list=field_list)
707 >>> print my_form
708 <tr><th>Default field 1:</th><td><input type="text" name="default_field_1" /></td></tr>
709 <tr><th>Default field 2:</th><td><input type="text" name="default_field_2" /></td></tr>
710 <tr><th>Field3:</th><td><input type="text" name="field3" /></td></tr>
711 <tr><th>Field4:</th><td><input type="text" name="field4" /></td></tr>
713 Similarly, changes to field attributes do not persist from one Form instance
714 to the next.
715 >>> class Person(Form):
716 ... first_name = CharField(required=False)
717 ... last_name = CharField(required=False)
718 ... def __init__(self, names_required=False, *args, **kwargs):
719 ... super(Person, self).__init__(*args, **kwargs)
720 ... if names_required:
721 ... self.fields['first_name'].required = True
722 ... self.fields['first_name'].widget.attrs['class'] = 'required'
723 ... self.fields['last_name'].required = True
724 ... self.fields['last_name'].widget.attrs['class'] = 'required'
725 >>> f = Person(names_required=False)
726 >>> f['first_name'].field.required, f['last_name'].field.required
727 (False, False)
728 >>> f['first_name'].field.widget.attrs, f['last_name'].field.widget.attrs
729 ({}, {})
730 >>> f = Person(names_required=True)
731 >>> f['first_name'].field.required, f['last_name'].field.required
732 (True, True)
733 >>> f['first_name'].field.widget.attrs, f['last_name'].field.widget.attrs
734 ({'class': 'required'}, {'class': 'required'})
735 >>> f = Person(names_required=False)
736 >>> f['first_name'].field.required, f['last_name'].field.required
737 (False, False)
738 >>> f['first_name'].field.widget.attrs, f['last_name'].field.widget.attrs
739 ({}, {})
740 >>> class Person(Form):
741 ... first_name = CharField(max_length=30)
742 ... last_name = CharField(max_length=30)
743 ... def __init__(self, name_max_length=None, *args, **kwargs):
744 ... super(Person, self).__init__(*args, **kwargs)
745 ... if name_max_length:
746 ... self.fields['first_name'].max_length = name_max_length
747 ... self.fields['last_name'].max_length = name_max_length
748 >>> f = Person(name_max_length=None)
749 >>> f['first_name'].field.max_length, f['last_name'].field.max_length
750 (30, 30)
751 >>> f = Person(name_max_length=20)
752 >>> f['first_name'].field.max_length, f['last_name'].field.max_length
753 (20, 20)
754 >>> f = Person(name_max_length=None)
755 >>> f['first_name'].field.max_length, f['last_name'].field.max_length
756 (30, 30)
758 HiddenInput widgets are displayed differently in the as_table(), as_ul()
759 and as_p() output of a Form -- their verbose names are not displayed, and a
760 separate row is not displayed. They're displayed in the last row of the
761 form, directly after that row's form element.
762 >>> class Person(Form):
763 ... first_name = CharField()
764 ... last_name = CharField()
765 ... hidden_text = CharField(widget=HiddenInput)
766 ... birthday = DateField()
767 >>> p = Person(auto_id=False)
768 >>> print p
769 <tr><th>First name:</th><td><input type="text" name="first_name" /></td></tr>
770 <tr><th>Last name:</th><td><input type="text" name="last_name" /></td></tr>
771 <tr><th>Birthday:</th><td><input type="text" name="birthday" /><input type="hidden" name="hidden_text" /></td></tr>
772 >>> print p.as_ul()
773 <li>First name: <input type="text" name="first_name" /></li>
774 <li>Last name: <input type="text" name="last_name" /></li>
775 <li>Birthday: <input type="text" name="birthday" /><input type="hidden" name="hidden_text" /></li>
776 >>> print p.as_p()
777 <p>First name: <input type="text" name="first_name" /></p>
778 <p>Last name: <input type="text" name="last_name" /></p>
779 <p>Birthday: <input type="text" name="birthday" /><input type="hidden" name="hidden_text" /></p>
781 With auto_id set, a HiddenInput still gets an ID, but it doesn't get a label.
782 >>> p = Person(auto_id='id_%s')
783 >>> print p
784 <tr><th><label for="id_first_name">First name:</label></th><td><input type="text" name="first_name" id="id_first_name" /></td></tr>
785 <tr><th><label for="id_last_name">Last name:</label></th><td><input type="text" name="last_name" id="id_last_name" /></td></tr>
786 <tr><th><label for="id_birthday">Birthday:</label></th><td><input type="text" name="birthday" id="id_birthday" /><input type="hidden" name="hidden_text" id="id_hidden_text" /></td></tr>
787 >>> print p.as_ul()
788 <li><label for="id_first_name">First name:</label> <input type="text" name="first_name" id="id_first_name" /></li>
789 <li><label for="id_last_name">Last name:</label> <input type="text" name="last_name" id="id_last_name" /></li>
790 <li><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" id="id_birthday" /><input type="hidden" name="hidden_text" id="id_hidden_text" /></li>
791 >>> print p.as_p()
792 <p><label for="id_first_name">First name:</label> <input type="text" name="first_name" id="id_first_name" /></p>
793 <p><label for="id_last_name">Last name:</label> <input type="text" name="last_name" id="id_last_name" /></p>
794 <p><label for="id_birthday">Birthday:</label> <input type="text" name="birthday" id="id_birthday" /><input type="hidden" name="hidden_text" id="id_hidden_text" /></p>
796 If a field with a HiddenInput has errors, the as_table() and as_ul() output
797 will include the error message(s) with the text "(Hidden field [fieldname]) "
798 prepended. This message is displayed at the top of the output, regardless of
799 its field's order in the form.
800 >>> p = Person({'first_name': 'John', 'last_name': 'Lennon', 'birthday': '1940-10-9'}, auto_id=False)
801 >>> print p
802 <tr><td colspan="2"><ul class="errorlist"><li>(Hidden field hidden_text) This field is required.</li></ul></td></tr>
803 <tr><th>First name:</th><td><input type="text" name="first_name" value="John" /></td></tr>
804 <tr><th>Last name:</th><td><input type="text" name="last_name" value="Lennon" /></td></tr>
805 <tr><th>Birthday:</th><td><input type="text" name="birthday" value="1940-10-9" /><input type="hidden" name="hidden_text" /></td></tr>
806 >>> print p.as_ul()
807 <li><ul class="errorlist"><li>(Hidden field hidden_text) This field is required.</li></ul></li>
808 <li>First name: <input type="text" name="first_name" value="John" /></li>
809 <li>Last name: <input type="text" name="last_name" value="Lennon" /></li>
810 <li>Birthday: <input type="text" name="birthday" value="1940-10-9" /><input type="hidden" name="hidden_text" /></li>
811 >>> print p.as_p()
812 <ul class="errorlist"><li>(Hidden field hidden_text) This field is required.</li></ul>
813 <p>First name: <input type="text" name="first_name" value="John" /></p>
814 <p>Last name: <input type="text" name="last_name" value="Lennon" /></p>
815 <p>Birthday: <input type="text" name="birthday" value="1940-10-9" /><input type="hidden" name="hidden_text" /></p>
817 A corner case: It's possible for a form to have only HiddenInputs.
818 >>> class TestForm(Form):
819 ... foo = CharField(widget=HiddenInput)
820 ... bar = CharField(widget=HiddenInput)
821 >>> p = TestForm(auto_id=False)
822 >>> print p.as_table()
823 <input type="hidden" name="foo" /><input type="hidden" name="bar" />
824 >>> print p.as_ul()
825 <input type="hidden" name="foo" /><input type="hidden" name="bar" />
826 >>> print p.as_p()
827 <input type="hidden" name="foo" /><input type="hidden" name="bar" />
829 A Form's fields are displayed in the same order in which they were defined.
830 >>> class TestForm(Form):
831 ... field1 = CharField()
832 ... field2 = CharField()
833 ... field3 = CharField()
834 ... field4 = CharField()
835 ... field5 = CharField()
836 ... field6 = CharField()
837 ... field7 = CharField()
838 ... field8 = CharField()
839 ... field9 = CharField()
840 ... field10 = CharField()
841 ... field11 = CharField()
842 ... field12 = CharField()
843 ... field13 = CharField()
844 ... field14 = CharField()
845 >>> p = TestForm(auto_id=False)
846 >>> print p
847 <tr><th>Field1:</th><td><input type="text" name="field1" /></td></tr>
848 <tr><th>Field2:</th><td><input type="text" name="field2" /></td></tr>
849 <tr><th>Field3:</th><td><input type="text" name="field3" /></td></tr>
850 <tr><th>Field4:</th><td><input type="text" name="field4" /></td></tr>
851 <tr><th>Field5:</th><td><input type="text" name="field5" /></td></tr>
852 <tr><th>Field6:</th><td><input type="text" name="field6" /></td></tr>
853 <tr><th>Field7:</th><td><input type="text" name="field7" /></td></tr>
854 <tr><th>Field8:</th><td><input type="text" name="field8" /></td></tr>
855 <tr><th>Field9:</th><td><input type="text" name="field9" /></td></tr>
856 <tr><th>Field10:</th><td><input type="text" name="field10" /></td></tr>
857 <tr><th>Field11:</th><td><input type="text" name="field11" /></td></tr>
858 <tr><th>Field12:</th><td><input type="text" name="field12" /></td></tr>
859 <tr><th>Field13:</th><td><input type="text" name="field13" /></td></tr>
860 <tr><th>Field14:</th><td><input type="text" name="field14" /></td></tr>
862 Some Field classes have an effect on the HTML attributes of their associated
863 Widget. If you set max_length in a CharField and its associated widget is
864 either a TextInput or PasswordInput, then the widget's rendered HTML will
865 include the "maxlength" attribute.
866 >>> class UserRegistration(Form):
867 ... username = CharField(max_length=10) # uses TextInput by default
868 ... password = CharField(max_length=10, widget=PasswordInput)
869 ... realname = CharField(max_length=10, widget=TextInput) # redundantly define widget, just to test
870 ... address = CharField() # no max_length defined here
871 >>> p = UserRegistration(auto_id=False)
872 >>> print p.as_ul()
873 <li>Username: <input type="text" name="username" maxlength="10" /></li>
874 <li>Password: <input type="password" name="password" maxlength="10" /></li>
875 <li>Realname: <input type="text" name="realname" maxlength="10" /></li>
876 <li>Address: <input type="text" name="address" /></li>
878 If you specify a custom "attrs" that includes the "maxlength" attribute,
879 the Field's max_length attribute will override whatever "maxlength" you specify
880 in "attrs".
881 >>> class UserRegistration(Form):
882 ... username = CharField(max_length=10, widget=TextInput(attrs={'maxlength': 20}))
883 ... password = CharField(max_length=10, widget=PasswordInput)
884 >>> p = UserRegistration(auto_id=False)
885 >>> print p.as_ul()
886 <li>Username: <input type="text" name="username" maxlength="10" /></li>
887 <li>Password: <input type="password" name="password" maxlength="10" /></li>
889 # Specifying labels ###########################################################
891 You can specify the label for a field by using the 'label' argument to a Field
892 class. If you don't specify 'label', Django will use the field name with
893 underscores converted to spaces, and the initial letter capitalized.
894 >>> class UserRegistration(Form):
895 ... username = CharField(max_length=10, label='Your username')
896 ... password1 = CharField(widget=PasswordInput)
897 ... password2 = CharField(widget=PasswordInput, label='Password (again)')
898 >>> p = UserRegistration(auto_id=False)
899 >>> print p.as_ul()
900 <li>Your username: <input type="text" name="username" maxlength="10" /></li>
901 <li>Password1: <input type="password" name="password1" /></li>
902 <li>Password (again): <input type="password" name="password2" /></li>
904 Labels for as_* methods will only end in a colon if they don't end in other
905 punctuation already.
906 >>> class Questions(Form):
907 ... q1 = CharField(label='The first question')
908 ... q2 = CharField(label='What is your name?')
909 ... q3 = CharField(label='The answer to life is:')
910 ... q4 = CharField(label='Answer this question!')
911 ... q5 = CharField(label='The last question. Period.')
912 >>> print Questions(auto_id=False).as_p()
913 <p>The first question: <input type="text" name="q1" /></p>
914 <p>What is your name? <input type="text" name="q2" /></p>
915 <p>The answer to life is: <input type="text" name="q3" /></p>
916 <p>Answer this question! <input type="text" name="q4" /></p>
917 <p>The last question. Period. <input type="text" name="q5" /></p>
918 >>> print Questions().as_p()
919 <p><label for="id_q1">The first question:</label> <input type="text" name="q1" id="id_q1" /></p>
920 <p><label for="id_q2">What is your name?</label> <input type="text" name="q2" id="id_q2" /></p>
921 <p><label for="id_q3">The answer to life is:</label> <input type="text" name="q3" id="id_q3" /></p>
922 <p><label for="id_q4">Answer this question!</label> <input type="text" name="q4" id="id_q4" /></p>
923 <p><label for="id_q5">The last question. Period.</label> <input type="text" name="q5" id="id_q5" /></p>
925 A label can be a Unicode object or a bytestring with special characters.
926 >>> class UserRegistration(Form):
927 ... username = CharField(max_length=10, label='ŠĐĆŽćžšđ')
928 ... password = CharField(widget=PasswordInput, label=u'\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111')
929 >>> p = UserRegistration(auto_id=False)
930 >>> p.as_ul()
931 u'<li>\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111: <input type="text" name="username" maxlength="10" /></li>\n<li>\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111: <input type="password" name="password" /></li>'
933 If a label is set to the empty string for a field, that field won't get a label.
934 >>> class UserRegistration(Form):
935 ... username = CharField(max_length=10, label='')
936 ... password = CharField(widget=PasswordInput)
937 >>> p = UserRegistration(auto_id=False)
938 >>> print p.as_ul()
939 <li> <input type="text" name="username" maxlength="10" /></li>
940 <li>Password: <input type="password" name="password" /></li>
941 >>> p = UserRegistration(auto_id='id_%s')
942 >>> print p.as_ul()
943 <li> <input id="id_username" type="text" name="username" maxlength="10" /></li>
944 <li><label for="id_password">Password:</label> <input type="password" name="password" id="id_password" /></li>
946 If label is None, Django will auto-create the label from the field name. This
947 is default behavior.
948 >>> class UserRegistration(Form):
949 ... username = CharField(max_length=10, label=None)
950 ... password = CharField(widget=PasswordInput)
951 >>> p = UserRegistration(auto_id=False)
952 >>> print p.as_ul()
953 <li>Username: <input type="text" name="username" maxlength="10" /></li>
954 <li>Password: <input type="password" name="password" /></li>
955 >>> p = UserRegistration(auto_id='id_%s')
956 >>> print p.as_ul()
957 <li><label for="id_username">Username:</label> <input id="id_username" type="text" name="username" maxlength="10" /></li>
958 <li><label for="id_password">Password:</label> <input type="password" name="password" id="id_password" /></li>
961 # Label Suffix ################################################################
963 You can specify the 'label_suffix' argument to a Form class to modify the
964 punctuation symbol used at the end of a label. By default, the colon (:) is
965 used, and is only appended to the label if the label doesn't already end with a
966 punctuation symbol: ., !, ? or :. If you specify a different suffix, it will
967 be appended regardless of the last character of the label.
969 >>> class FavoriteForm(Form):
970 ... color = CharField(label='Favorite color?')
971 ... animal = CharField(label='Favorite animal')
973 >>> f = FavoriteForm(auto_id=False)
974 >>> print f.as_ul()
975 <li>Favorite color? <input type="text" name="color" /></li>
976 <li>Favorite animal: <input type="text" name="animal" /></li>
977 >>> f = FavoriteForm(auto_id=False, label_suffix='?')
978 >>> print f.as_ul()
979 <li>Favorite color? <input type="text" name="color" /></li>
980 <li>Favorite animal? <input type="text" name="animal" /></li>
981 >>> f = FavoriteForm(auto_id=False, label_suffix='')
982 >>> print f.as_ul()
983 <li>Favorite color? <input type="text" name="color" /></li>
984 <li>Favorite animal <input type="text" name="animal" /></li>
985 >>> f = FavoriteForm(auto_id=False, label_suffix=u'\u2192')
986 >>> f.as_ul()
987 u'<li>Favorite color? <input type="text" name="color" /></li>\n<li>Favorite animal\u2192 <input type="text" name="animal" /></li>'
989 """ + \
990 r""" # [This concatenation is to keep the string below the jython's 32K limit].
992 # Initial data ################################################################
994 You can specify initial data for a field by using the 'initial' argument to a
995 Field class. This initial data is displayed when a Form is rendered with *no*
996 data. It is not displayed when a Form is rendered with any data (including an
997 empty dictionary). Also, the initial value is *not* used if data for a
998 particular required field isn't provided.
999 >>> class UserRegistration(Form):
1000 ... username = CharField(max_length=10, initial='django')
1001 ... password = CharField(widget=PasswordInput)
1003 Here, we're not submitting any data, so the initial value will be displayed.
1004 >>> p = UserRegistration(auto_id=False)
1005 >>> print p.as_ul()
1006 <li>Username: <input type="text" name="username" value="django" maxlength="10" /></li>
1007 <li>Password: <input type="password" name="password" /></li>
1009 Here, we're submitting data, so the initial value will *not* be displayed.
1010 >>> p = UserRegistration({}, auto_id=False)
1011 >>> print p.as_ul()
1012 <li><ul class="errorlist"><li>This field is required.</li></ul>Username: <input type="text" name="username" maxlength="10" /></li>
1013 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1014 >>> p = UserRegistration({'username': u''}, auto_id=False)
1015 >>> print p.as_ul()
1016 <li><ul class="errorlist"><li>This field is required.</li></ul>Username: <input type="text" name="username" maxlength="10" /></li>
1017 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1018 >>> p = UserRegistration({'username': u'foo'}, auto_id=False)
1019 >>> print p.as_ul()
1020 <li>Username: <input type="text" name="username" value="foo" maxlength="10" /></li>
1021 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1023 An 'initial' value is *not* used as a fallback if data is not provided. In this
1024 example, we don't provide a value for 'username', and the form raises a
1025 validation error rather than using the initial value for 'username'.
1026 >>> p = UserRegistration({'password': 'secret'})
1027 >>> p.errors
1028 {'username': [u'This field is required.']}
1029 >>> p.is_valid()
1030 False
1032 # Dynamic initial data ########################################################
1034 The previous technique dealt with "hard-coded" initial data, but it's also
1035 possible to specify initial data after you've already created the Form class
1036 (i.e., at runtime). Use the 'initial' parameter to the Form constructor. This
1037 should be a dictionary containing initial values for one or more fields in the
1038 form, keyed by field name.
1040 >>> class UserRegistration(Form):
1041 ... username = CharField(max_length=10)
1042 ... password = CharField(widget=PasswordInput)
1044 Here, we're not submitting any data, so the initial value will be displayed.
1045 >>> p = UserRegistration(initial={'username': 'django'}, auto_id=False)
1046 >>> print p.as_ul()
1047 <li>Username: <input type="text" name="username" value="django" maxlength="10" /></li>
1048 <li>Password: <input type="password" name="password" /></li>
1049 >>> p = UserRegistration(initial={'username': 'stephane'}, auto_id=False)
1050 >>> print p.as_ul()
1051 <li>Username: <input type="text" name="username" value="stephane" maxlength="10" /></li>
1052 <li>Password: <input type="password" name="password" /></li>
1054 The 'initial' parameter is meaningless if you pass data.
1055 >>> p = UserRegistration({}, initial={'username': 'django'}, auto_id=False)
1056 >>> print p.as_ul()
1057 <li><ul class="errorlist"><li>This field is required.</li></ul>Username: <input type="text" name="username" maxlength="10" /></li>
1058 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1059 >>> p = UserRegistration({'username': u''}, initial={'username': 'django'}, auto_id=False)
1060 >>> print p.as_ul()
1061 <li><ul class="errorlist"><li>This field is required.</li></ul>Username: <input type="text" name="username" maxlength="10" /></li>
1062 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1063 >>> p = UserRegistration({'username': u'foo'}, initial={'username': 'django'}, auto_id=False)
1064 >>> print p.as_ul()
1065 <li>Username: <input type="text" name="username" value="foo" maxlength="10" /></li>
1066 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1068 A dynamic 'initial' value is *not* used as a fallback if data is not provided.
1069 In this example, we don't provide a value for 'username', and the form raises a
1070 validation error rather than using the initial value for 'username'.
1071 >>> p = UserRegistration({'password': 'secret'}, initial={'username': 'django'})
1072 >>> p.errors
1073 {'username': [u'This field is required.']}
1074 >>> p.is_valid()
1075 False
1077 If a Form defines 'initial' *and* 'initial' is passed as a parameter to Form(),
1078 then the latter will get precedence.
1079 >>> class UserRegistration(Form):
1080 ... username = CharField(max_length=10, initial='django')
1081 ... password = CharField(widget=PasswordInput)
1082 >>> p = UserRegistration(initial={'username': 'babik'}, auto_id=False)
1083 >>> print p.as_ul()
1084 <li>Username: <input type="text" name="username" value="babik" maxlength="10" /></li>
1085 <li>Password: <input type="password" name="password" /></li>
1087 # Callable initial data ########################################################
1089 The previous technique dealt with raw values as initial data, but it's also
1090 possible to specify callable data.
1092 >>> class UserRegistration(Form):
1093 ... username = CharField(max_length=10)
1094 ... password = CharField(widget=PasswordInput)
1096 We need to define functions that get called later.
1097 >>> def initial_django():
1098 ... return 'django'
1099 >>> def initial_stephane():
1100 ... return 'stephane'
1102 Here, we're not submitting any data, so the initial value will be displayed.
1103 >>> p = UserRegistration(initial={'username': initial_django}, auto_id=False)
1104 >>> print p.as_ul()
1105 <li>Username: <input type="text" name="username" value="django" maxlength="10" /></li>
1106 <li>Password: <input type="password" name="password" /></li>
1108 The 'initial' parameter is meaningless if you pass data.
1109 >>> p = UserRegistration({}, initial={'username': initial_django}, auto_id=False)
1110 >>> print p.as_ul()
1111 <li><ul class="errorlist"><li>This field is required.</li></ul>Username: <input type="text" name="username" maxlength="10" /></li>
1112 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1113 >>> p = UserRegistration({'username': u''}, initial={'username': initial_django}, auto_id=False)
1114 >>> print p.as_ul()
1115 <li><ul class="errorlist"><li>This field is required.</li></ul>Username: <input type="text" name="username" maxlength="10" /></li>
1116 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1117 >>> p = UserRegistration({'username': u'foo'}, initial={'username': initial_django}, auto_id=False)
1118 >>> print p.as_ul()
1119 <li>Username: <input type="text" name="username" value="foo" maxlength="10" /></li>
1120 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /></li>
1122 A callable 'initial' value is *not* used as a fallback if data is not provided.
1123 In this example, we don't provide a value for 'username', and the form raises a
1124 validation error rather than using the initial value for 'username'.
1125 >>> p = UserRegistration({'password': 'secret'}, initial={'username': initial_django})
1126 >>> p.errors
1127 {'username': [u'This field is required.']}
1128 >>> p.is_valid()
1129 False
1131 If a Form defines 'initial' *and* 'initial' is passed as a parameter to Form(),
1132 then the latter will get precedence.
1133 >>> class UserRegistration(Form):
1134 ... username = CharField(max_length=10, initial=initial_django)
1135 ... password = CharField(widget=PasswordInput)
1136 >>> p = UserRegistration(auto_id=False)
1137 >>> print p.as_ul()
1138 <li>Username: <input type="text" name="username" value="django" maxlength="10" /></li>
1139 <li>Password: <input type="password" name="password" /></li>
1140 >>> p = UserRegistration(initial={'username': initial_stephane}, auto_id=False)
1141 >>> print p.as_ul()
1142 <li>Username: <input type="text" name="username" value="stephane" maxlength="10" /></li>
1143 <li>Password: <input type="password" name="password" /></li>
1145 # Help text ###################################################################
1147 You can specify descriptive text for a field by using the 'help_text' argument
1148 to a Field class. This help text is displayed when a Form is rendered.
1149 >>> class UserRegistration(Form):
1150 ... username = CharField(max_length=10, help_text='e.g., user@example.com')
1151 ... password = CharField(widget=PasswordInput, help_text='Choose wisely.')
1152 >>> p = UserRegistration(auto_id=False)
1153 >>> print p.as_ul()
1154 <li>Username: <input type="text" name="username" maxlength="10" /> e.g., user@example.com</li>
1155 <li>Password: <input type="password" name="password" /> Choose wisely.</li>
1156 >>> print p.as_p()
1157 <p>Username: <input type="text" name="username" maxlength="10" /> e.g., user@example.com</p>
1158 <p>Password: <input type="password" name="password" /> Choose wisely.</p>
1159 >>> print p.as_table()
1160 <tr><th>Username:</th><td><input type="text" name="username" maxlength="10" /><br />e.g., user@example.com</td></tr>
1161 <tr><th>Password:</th><td><input type="password" name="password" /><br />Choose wisely.</td></tr>
1163 The help text is displayed whether or not data is provided for the form.
1164 >>> p = UserRegistration({'username': u'foo'}, auto_id=False)
1165 >>> print p.as_ul()
1166 <li>Username: <input type="text" name="username" value="foo" maxlength="10" /> e.g., user@example.com</li>
1167 <li><ul class="errorlist"><li>This field is required.</li></ul>Password: <input type="password" name="password" /> Choose wisely.</li>
1169 help_text is not displayed for hidden fields. It can be used for documentation
1170 purposes, though.
1171 >>> class UserRegistration(Form):
1172 ... username = CharField(max_length=10, help_text='e.g., user@example.com')
1173 ... password = CharField(widget=PasswordInput)
1174 ... next = CharField(widget=HiddenInput, initial='/', help_text='Redirect destination')
1175 >>> p = UserRegistration(auto_id=False)
1176 >>> print p.as_ul()
1177 <li>Username: <input type="text" name="username" maxlength="10" /> e.g., user@example.com</li>
1178 <li>Password: <input type="password" name="password" /><input type="hidden" name="next" value="/" /></li>
1180 Help text can include arbitrary Unicode characters.
1181 >>> class UserRegistration(Form):
1182 ... username = CharField(max_length=10, help_text='ŠĐĆŽćžšđ')
1183 >>> p = UserRegistration(auto_id=False)
1184 >>> p.as_ul()
1185 u'<li>Username: <input type="text" name="username" maxlength="10" /> \u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111</li>'
1187 # Subclassing forms ###########################################################
1189 You can subclass a Form to add fields. The resulting form subclass will have
1190 all of the fields of the parent Form, plus whichever fields you define in the
1191 subclass.
1192 >>> class Person(Form):
1193 ... first_name = CharField()
1194 ... last_name = CharField()
1195 ... birthday = DateField()
1196 >>> class Musician(Person):
1197 ... instrument = CharField()
1198 >>> p = Person(auto_id=False)
1199 >>> print p.as_ul()
1200 <li>First name: <input type="text" name="first_name" /></li>
1201 <li>Last name: <input type="text" name="last_name" /></li>
1202 <li>Birthday: <input type="text" name="birthday" /></li>
1203 >>> m = Musician(auto_id=False)
1204 >>> print m.as_ul()
1205 <li>First name: <input type="text" name="first_name" /></li>
1206 <li>Last name: <input type="text" name="last_name" /></li>
1207 <li>Birthday: <input type="text" name="birthday" /></li>
1208 <li>Instrument: <input type="text" name="instrument" /></li>
1210 Yes, you can subclass multiple forms. The fields are added in the order in
1211 which the parent classes are listed.
1212 >>> class Person(Form):
1213 ... first_name = CharField()
1214 ... last_name = CharField()
1215 ... birthday = DateField()
1216 >>> class Instrument(Form):
1217 ... instrument = CharField()
1218 >>> class Beatle(Person, Instrument):
1219 ... haircut_type = CharField()
1220 >>> b = Beatle(auto_id=False)
1221 >>> print b.as_ul()
1222 <li>First name: <input type="text" name="first_name" /></li>
1223 <li>Last name: <input type="text" name="last_name" /></li>
1224 <li>Birthday: <input type="text" name="birthday" /></li>
1225 <li>Instrument: <input type="text" name="instrument" /></li>
1226 <li>Haircut type: <input type="text" name="haircut_type" /></li>
1228 # Forms with prefixes #########################################################
1230 Sometimes it's necessary to have multiple forms display on the same HTML page,
1231 or multiple copies of the same form. We can accomplish this with form prefixes.
1232 Pass the keyword argument 'prefix' to the Form constructor to use this feature.
1233 This value will be prepended to each HTML form field name. One way to think
1234 about this is "namespaces for HTML forms". Notice that in the data argument,
1235 each field's key has the prefix, in this case 'person1', prepended to the
1236 actual field name.
1237 >>> class Person(Form):
1238 ... first_name = CharField()
1239 ... last_name = CharField()
1240 ... birthday = DateField()
1241 >>> data = {
1242 ... 'person1-first_name': u'John',
1243 ... 'person1-last_name': u'Lennon',
1244 ... 'person1-birthday': u'1940-10-9'
1245 ... }
1246 >>> p = Person(data, prefix='person1')
1247 >>> print p.as_ul()
1248 <li><label for="id_person1-first_name">First name:</label> <input type="text" name="person1-first_name" value="John" id="id_person1-first_name" /></li>
1249 <li><label for="id_person1-last_name">Last name:</label> <input type="text" name="person1-last_name" value="Lennon" id="id_person1-last_name" /></li>
1250 <li><label for="id_person1-birthday">Birthday:</label> <input type="text" name="person1-birthday" value="1940-10-9" id="id_person1-birthday" /></li>
1251 >>> print p['first_name']
1252 <input type="text" name="person1-first_name" value="John" id="id_person1-first_name" />
1253 >>> print p['last_name']
1254 <input type="text" name="person1-last_name" value="Lennon" id="id_person1-last_name" />
1255 >>> print p['birthday']
1256 <input type="text" name="person1-birthday" value="1940-10-9" id="id_person1-birthday" />
1257 >>> p.errors
1259 >>> p.is_valid()
1260 True
1261 >>> p.cleaned_data
1262 {'first_name': u'John', 'last_name': u'Lennon', 'birthday': datetime.date(1940, 10, 9)}
1264 Let's try submitting some bad data to make sure form.errors and field.errors
1265 work as expected.
1266 >>> data = {
1267 ... 'person1-first_name': u'',
1268 ... 'person1-last_name': u'',
1269 ... 'person1-birthday': u''
1270 ... }
1271 >>> p = Person(data, prefix='person1')
1272 >>> p.errors
1273 {'first_name': [u'This field is required.'], 'last_name': [u'This field is required.'], 'birthday': [u'This field is required.']}
1274 >>> p['first_name'].errors
1275 [u'This field is required.']
1276 >>> p['person1-first_name'].errors
1277 Traceback (most recent call last):
1279 KeyError: "Key 'person1-first_name' not found in Form"
1281 In this example, the data doesn't have a prefix, but the form requires it, so
1282 the form doesn't "see" the fields.
1283 >>> data = {
1284 ... 'first_name': u'John',
1285 ... 'last_name': u'Lennon',
1286 ... 'birthday': u'1940-10-9'
1287 ... }
1288 >>> p = Person(data, prefix='person1')
1289 >>> p.errors
1290 {'first_name': [u'This field is required.'], 'last_name': [u'This field is required.'], 'birthday': [u'This field is required.']}
1292 With prefixes, a single data dictionary can hold data for multiple instances
1293 of the same form.
1294 >>> data = {
1295 ... 'person1-first_name': u'John',
1296 ... 'person1-last_name': u'Lennon',
1297 ... 'person1-birthday': u'1940-10-9',
1298 ... 'person2-first_name': u'Jim',
1299 ... 'person2-last_name': u'Morrison',
1300 ... 'person2-birthday': u'1943-12-8'
1301 ... }
1302 >>> p1 = Person(data, prefix='person1')
1303 >>> p1.is_valid()
1304 True
1305 >>> p1.cleaned_data
1306 {'first_name': u'John', 'last_name': u'Lennon', 'birthday': datetime.date(1940, 10, 9)}
1307 >>> p2 = Person(data, prefix='person2')
1308 >>> p2.is_valid()
1309 True
1310 >>> p2.cleaned_data
1311 {'first_name': u'Jim', 'last_name': u'Morrison', 'birthday': datetime.date(1943, 12, 8)}
1313 By default, forms append a hyphen between the prefix and the field name, but a
1314 form can alter that behavior by implementing the add_prefix() method. This
1315 method takes a field name and returns the prefixed field, according to
1316 self.prefix.
1317 >>> class Person(Form):
1318 ... first_name = CharField()
1319 ... last_name = CharField()
1320 ... birthday = DateField()
1321 ... def add_prefix(self, field_name):
1322 ... return self.prefix and '%s-prefix-%s' % (self.prefix, field_name) or field_name
1323 >>> p = Person(prefix='foo')
1324 >>> print p.as_ul()
1325 <li><label for="id_foo-prefix-first_name">First name:</label> <input type="text" name="foo-prefix-first_name" id="id_foo-prefix-first_name" /></li>
1326 <li><label for="id_foo-prefix-last_name">Last name:</label> <input type="text" name="foo-prefix-last_name" id="id_foo-prefix-last_name" /></li>
1327 <li><label for="id_foo-prefix-birthday">Birthday:</label> <input type="text" name="foo-prefix-birthday" id="id_foo-prefix-birthday" /></li>
1328 >>> data = {
1329 ... 'foo-prefix-first_name': u'John',
1330 ... 'foo-prefix-last_name': u'Lennon',
1331 ... 'foo-prefix-birthday': u'1940-10-9'
1332 ... }
1333 >>> p = Person(data, prefix='foo')
1334 >>> p.is_valid()
1335 True
1336 >>> p.cleaned_data
1337 {'first_name': u'John', 'last_name': u'Lennon', 'birthday': datetime.date(1940, 10, 9)}
1339 # Forms with NullBooleanFields ################################################
1341 NullBooleanField is a bit of a special case because its presentation (widget)
1342 is different than its data. This is handled transparently, though.
1344 >>> class Person(Form):
1345 ... name = CharField()
1346 ... is_cool = NullBooleanField()
1347 >>> p = Person({'name': u'Joe'}, auto_id=False)
1348 >>> print p['is_cool']
1349 <select name="is_cool">
1350 <option value="1" selected="selected">Unknown</option>
1351 <option value="2">Yes</option>
1352 <option value="3">No</option>
1353 </select>
1354 >>> p = Person({'name': u'Joe', 'is_cool': u'1'}, auto_id=False)
1355 >>> print p['is_cool']
1356 <select name="is_cool">
1357 <option value="1" selected="selected">Unknown</option>
1358 <option value="2">Yes</option>
1359 <option value="3">No</option>
1360 </select>
1361 >>> p = Person({'name': u'Joe', 'is_cool': u'2'}, auto_id=False)
1362 >>> print p['is_cool']
1363 <select name="is_cool">
1364 <option value="1">Unknown</option>
1365 <option value="2" selected="selected">Yes</option>
1366 <option value="3">No</option>
1367 </select>
1368 >>> p = Person({'name': u'Joe', 'is_cool': u'3'}, auto_id=False)
1369 >>> print p['is_cool']
1370 <select name="is_cool">
1371 <option value="1">Unknown</option>
1372 <option value="2">Yes</option>
1373 <option value="3" selected="selected">No</option>
1374 </select>
1375 >>> p = Person({'name': u'Joe', 'is_cool': True}, auto_id=False)
1376 >>> print p['is_cool']
1377 <select name="is_cool">
1378 <option value="1">Unknown</option>
1379 <option value="2" selected="selected">Yes</option>
1380 <option value="3">No</option>
1381 </select>
1382 >>> p = Person({'name': u'Joe', 'is_cool': False}, auto_id=False)
1383 >>> print p['is_cool']
1384 <select name="is_cool">
1385 <option value="1">Unknown</option>
1386 <option value="2">Yes</option>
1387 <option value="3" selected="selected">No</option>
1388 </select>
1390 # Forms with FileFields ################################################
1392 FileFields are a special case because they take their data from the request.FILES,
1393 not request.POST.
1395 >>> class FileForm(Form):
1396 ... file1 = FileField()
1397 >>> f = FileForm(auto_id=False)
1398 >>> print f
1399 <tr><th>File1:</th><td><input type="file" name="file1" /></td></tr>
1401 >>> f = FileForm(data={}, files={}, auto_id=False)
1402 >>> print f
1403 <tr><th>File1:</th><td><ul class="errorlist"><li>This field is required.</li></ul><input type="file" name="file1" /></td></tr>
1405 >>> f = FileForm(data={}, files={'file1': {'filename': 'name', 'content':''}}, auto_id=False)
1406 >>> print f
1407 <tr><th>File1:</th><td><ul class="errorlist"><li>The submitted file is empty.</li></ul><input type="file" name="file1" /></td></tr>
1409 >>> f = FileForm(data={}, files={'file1': 'something that is not a file'}, auto_id=False)
1410 >>> print f
1411 <tr><th>File1:</th><td><ul class="errorlist"><li>No file was submitted. Check the encoding type on the form.</li></ul><input type="file" name="file1" /></td></tr>
1413 >>> f = FileForm(data={}, files={'file1': {'filename': 'name', 'content':'some content'}}, auto_id=False)
1414 >>> print f
1415 <tr><th>File1:</th><td><input type="file" name="file1" /></td></tr>
1416 >>> f.is_valid()
1417 True
1419 # Basic form processing in a view #############################################
1421 >>> from django.template import Template, Context
1422 >>> class UserRegistration(Form):
1423 ... username = CharField(max_length=10)
1424 ... password1 = CharField(widget=PasswordInput)
1425 ... password2 = CharField(widget=PasswordInput)
1426 ... def clean(self):
1427 ... if self.cleaned_data.get('password1') and self.cleaned_data.get('password2') and self.cleaned_data['password1'] != self.cleaned_data['password2']:
1428 ... raise ValidationError(u'Please make sure your passwords match.')
1429 ... return self.cleaned_data
1430 >>> def my_function(method, post_data):
1431 ... if method == 'POST':
1432 ... form = UserRegistration(post_data, auto_id=False)
1433 ... else:
1434 ... form = UserRegistration(auto_id=False)
1435 ... if form.is_valid():
1436 ... return 'VALID: %r' % form.cleaned_data
1437 ... t = Template('<form action="" method="post">\n<table>\n{{ form }}\n</table>\n<input type="submit" />\n</form>')
1438 ... return t.render(Context({'form': form}))
1440 Case 1: GET (an empty form, with no errors).
1441 >>> print my_function('GET', {})
1442 <form action="" method="post">
1443 <table>
1444 <tr><th>Username:</th><td><input type="text" name="username" maxlength="10" /></td></tr>
1445 <tr><th>Password1:</th><td><input type="password" name="password1" /></td></tr>
1446 <tr><th>Password2:</th><td><input type="password" name="password2" /></td></tr>
1447 </table>
1448 <input type="submit" />
1449 </form>
1451 Case 2: POST with erroneous data (a redisplayed form, with errors).
1452 >>> print my_function('POST', {'username': 'this-is-a-long-username', 'password1': 'foo', 'password2': 'bar'})
1453 <form action="" method="post">
1454 <table>
1455 <tr><td colspan="2"><ul class="errorlist"><li>Please make sure your passwords match.</li></ul></td></tr>
1456 <tr><th>Username:</th><td><ul class="errorlist"><li>Ensure this value has at most 10 characters (it has 23).</li></ul><input type="text" name="username" value="this-is-a-long-username" maxlength="10" /></td></tr>
1457 <tr><th>Password1:</th><td><input type="password" name="password1" value="foo" /></td></tr>
1458 <tr><th>Password2:</th><td><input type="password" name="password2" value="bar" /></td></tr>
1459 </table>
1460 <input type="submit" />
1461 </form>
1463 Case 3: POST with valid data (the success message).
1464 >>> print my_function('POST', {'username': 'adrian', 'password1': 'secret', 'password2': 'secret'})
1465 VALID: {'username': u'adrian', 'password1': u'secret', 'password2': u'secret'}
1467 # Some ideas for using templates with forms ###################################
1469 >>> class UserRegistration(Form):
1470 ... username = CharField(max_length=10, help_text="Good luck picking a username that doesn't already exist.")
1471 ... password1 = CharField(widget=PasswordInput)
1472 ... password2 = CharField(widget=PasswordInput)
1473 ... def clean(self):
1474 ... if self.cleaned_data.get('password1') and self.cleaned_data.get('password2') and self.cleaned_data['password1'] != self.cleaned_data['password2']:
1475 ... raise ValidationError(u'Please make sure your passwords match.')
1476 ... return self.cleaned_data
1478 You have full flexibility in displaying form fields in a template. Just pass a
1479 Form instance to the template, and use "dot" access to refer to individual
1480 fields. Note, however, that this flexibility comes with the responsibility of
1481 displaying all the errors, including any that might not be associated with a
1482 particular field.
1483 >>> t = Template('''<form action="">
1484 ... {{ form.username.errors.as_ul }}<p><label>Your username: {{ form.username }}</label></p>
1485 ... {{ form.password1.errors.as_ul }}<p><label>Password: {{ form.password1 }}</label></p>
1486 ... {{ form.password2.errors.as_ul }}<p><label>Password (again): {{ form.password2 }}</label></p>
1487 ... <input type="submit" />
1488 ... </form>''')
1489 >>> print t.render(Context({'form': UserRegistration(auto_id=False)}))
1490 <form action="">
1491 <p><label>Your username: <input type="text" name="username" maxlength="10" /></label></p>
1492 <p><label>Password: <input type="password" name="password1" /></label></p>
1493 <p><label>Password (again): <input type="password" name="password2" /></label></p>
1494 <input type="submit" />
1495 </form>
1496 >>> print t.render(Context({'form': UserRegistration({'username': 'django'}, auto_id=False)}))
1497 <form action="">
1498 <p><label>Your username: <input type="text" name="username" value="django" maxlength="10" /></label></p>
1499 <ul class="errorlist"><li>This field is required.</li></ul><p><label>Password: <input type="password" name="password1" /></label></p>
1500 <ul class="errorlist"><li>This field is required.</li></ul><p><label>Password (again): <input type="password" name="password2" /></label></p>
1501 <input type="submit" />
1502 </form>
1504 Use form.[field].label to output a field's label. You can specify the label for
1505 a field by using the 'label' argument to a Field class. If you don't specify
1506 'label', Django will use the field name with underscores converted to spaces,
1507 and the initial letter capitalized.
1508 >>> t = Template('''<form action="">
1509 ... <p><label>{{ form.username.label }}: {{ form.username }}</label></p>
1510 ... <p><label>{{ form.password1.label }}: {{ form.password1 }}</label></p>
1511 ... <p><label>{{ form.password2.label }}: {{ form.password2 }}</label></p>
1512 ... <input type="submit" />
1513 ... </form>''')
1514 >>> print t.render(Context({'form': UserRegistration(auto_id=False)}))
1515 <form action="">
1516 <p><label>Username: <input type="text" name="username" maxlength="10" /></label></p>
1517 <p><label>Password1: <input type="password" name="password1" /></label></p>
1518 <p><label>Password2: <input type="password" name="password2" /></label></p>
1519 <input type="submit" />
1520 </form>
1522 User form.[field].label_tag to output a field's label with a <label> tag
1523 wrapped around it, but *only* if the given field has an "id" attribute.
1524 Recall from above that passing the "auto_id" argument to a Form gives each
1525 field an "id" attribute.
1526 >>> t = Template('''<form action="">
1527 ... <p>{{ form.username.label_tag }}: {{ form.username }}</p>
1528 ... <p>{{ form.password1.label_tag }}: {{ form.password1 }}</p>
1529 ... <p>{{ form.password2.label_tag }}: {{ form.password2 }}</p>
1530 ... <input type="submit" />
1531 ... </form>''')
1532 >>> print t.render(Context({'form': UserRegistration(auto_id=False)}))
1533 <form action="">
1534 <p>Username: <input type="text" name="username" maxlength="10" /></p>
1535 <p>Password1: <input type="password" name="password1" /></p>
1536 <p>Password2: <input type="password" name="password2" /></p>
1537 <input type="submit" />
1538 </form>
1539 >>> print t.render(Context({'form': UserRegistration(auto_id='id_%s')}))
1540 <form action="">
1541 <p><label for="id_username">Username</label>: <input id="id_username" type="text" name="username" maxlength="10" /></p>
1542 <p><label for="id_password1">Password1</label>: <input type="password" name="password1" id="id_password1" /></p>
1543 <p><label for="id_password2">Password2</label>: <input type="password" name="password2" id="id_password2" /></p>
1544 <input type="submit" />
1545 </form>
1547 User form.[field].help_text to output a field's help text. If the given field
1548 does not have help text, nothing will be output.
1549 >>> t = Template('''<form action="">
1550 ... <p>{{ form.username.label_tag }}: {{ form.username }}<br />{{ form.username.help_text }}</p>
1551 ... <p>{{ form.password1.label_tag }}: {{ form.password1 }}</p>
1552 ... <p>{{ form.password2.label_tag }}: {{ form.password2 }}</p>
1553 ... <input type="submit" />
1554 ... </form>''')
1555 >>> print t.render(Context({'form': UserRegistration(auto_id=False)}))
1556 <form action="">
1557 <p>Username: <input type="text" name="username" maxlength="10" /><br />Good luck picking a username that doesn&#39;t already exist.</p>
1558 <p>Password1: <input type="password" name="password1" /></p>
1559 <p>Password2: <input type="password" name="password2" /></p>
1560 <input type="submit" />
1561 </form>
1562 >>> Template('{{ form.password1.help_text }}').render(Context({'form': UserRegistration(auto_id=False)}))
1565 The label_tag() method takes an optional attrs argument: a dictionary of HTML
1566 attributes to add to the <label> tag.
1567 >>> f = UserRegistration(auto_id='id_%s')
1568 >>> for bf in f:
1569 ... print bf.label_tag(attrs={'class': 'pretty'})
1570 <label for="id_username" class="pretty">Username</label>
1571 <label for="id_password1" class="pretty">Password1</label>
1572 <label for="id_password2" class="pretty">Password2</label>
1574 To display the errors that aren't associated with a particular field -- e.g.,
1575 the errors caused by Form.clean() -- use {{ form.non_field_errors }} in the
1576 template. If used on its own, it is displayed as a <ul> (or an empty string, if
1577 the list of errors is empty). You can also use it in {% if %} statements.
1578 >>> t = Template('''<form action="">
1579 ... {{ form.username.errors.as_ul }}<p><label>Your username: {{ form.username }}</label></p>
1580 ... {{ form.password1.errors.as_ul }}<p><label>Password: {{ form.password1 }}</label></p>
1581 ... {{ form.password2.errors.as_ul }}<p><label>Password (again): {{ form.password2 }}</label></p>
1582 ... <input type="submit" />
1583 ... </form>''')
1584 >>> print t.render(Context({'form': UserRegistration({'username': 'django', 'password1': 'foo', 'password2': 'bar'}, auto_id=False)}))
1585 <form action="">
1586 <p><label>Your username: <input type="text" name="username" value="django" maxlength="10" /></label></p>
1587 <p><label>Password: <input type="password" name="password1" value="foo" /></label></p>
1588 <p><label>Password (again): <input type="password" name="password2" value="bar" /></label></p>
1589 <input type="submit" />
1590 </form>
1591 >>> t = Template('''<form action="">
1592 ... {{ form.non_field_errors }}
1593 ... {{ form.username.errors.as_ul }}<p><label>Your username: {{ form.username }}</label></p>
1594 ... {{ form.password1.errors.as_ul }}<p><label>Password: {{ form.password1 }}</label></p>
1595 ... {{ form.password2.errors.as_ul }}<p><label>Password (again): {{ form.password2 }}</label></p>
1596 ... <input type="submit" />
1597 ... </form>''')
1598 >>> print t.render(Context({'form': UserRegistration({'username': 'django', 'password1': 'foo', 'password2': 'bar'}, auto_id=False)}))
1599 <form action="">
1600 <ul class="errorlist"><li>Please make sure your passwords match.</li></ul>
1601 <p><label>Your username: <input type="text" name="username" value="django" maxlength="10" /></label></p>
1602 <p><label>Password: <input type="password" name="password1" value="foo" /></label></p>
1603 <p><label>Password (again): <input type="password" name="password2" value="bar" /></label></p>
1604 <input type="submit" />
1605 </form>