{"id":75671,"date":"2020-01-20T11:28:57","date_gmt":"2020-01-20T05:58:57","guid":{"rendered":"https:\/\/www.vskills.in\/certification\/tutorial\/?p=75671"},"modified":"2024-04-12T14:17:14","modified_gmt":"2024-04-12T08:47:14","slug":"the-perfect-form","status":"publish","type":"page","link":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/","title":{"rendered":"The \u201cPerfect Form\u201d"},"content":{"rendered":"<p>Forms can often be a major cause of frustration for the users of your site. Let\u2019s consider the behavior of a hypothetical perfect form:<\/p>\n<ul>\n<li>It should ask the user for some information, obviously. Accessibility and usability matter here, so smart use of the HTML &lt;label&gt; element and useful contextual help are important.<\/li>\n<li>The submitted data should be subjected to extensive validation. The golden rule of Web application security is \u201cnever trust incoming data,\u201d so validation is essential.<\/li>\n<li>If the user has made any mistakes, the form should be redisplayed with detailed, informative error messages. The original data should be prefilled, to save the user from having to reenter everything.<\/li>\n<li>The form should continue to redisplay until all of the fields have been correctly filled.<\/li>\n<\/ul>\n<p>Constructing the perfect form seems like a lot of work! Thankfully, Django\u2019s forms framework is designed to do most of the work for you. You provide a description of the form\u2019s fields, validation rules, and a simple template, and Django does the rest. The result is a \u201cperfect form\u201d with very little effort.<\/p>\n<p>Creating a Feedback Form &#8211; The best way to build a site that people love is to listen to their feedback. Many sites appear to have forgotten this; they hide their contact details behind layers of FAQs, and they seem to make it as difficult as possible to get in touch with an actual human being.<\/p>\n<p>When your site has millions of users, this may be a reasonable strategy. When you\u2019re trying to build up an audience, though, you should actively encourage feedback at every opportunity. Let\u2019s build a simple feedback form and use it to illustrate Django\u2019s forms framework in action.<br>\nWe\u2019ll start by adding adding (r&#8217;^contact\/$&#8217;, &#8216;mysite.books.views.contact&#8217;) to the URLconf, then defining our form. Forms in Django are created in a similar way to models: declaratively, using a Python class. Here\u2019s the class for our simple form. By convention, we\u2019ll insert it into a new forms.py file within our application directory:<\/p>\n<p>from django import newforms as forms<\/p>\n<p>TOPIC_CHOICES = (<br>\n(&#8216;general&#8217;, &#8216;General enquiry&#8217;),<br>\n(&#8216;bug&#8217;, &#8216;Bug report&#8217;),<br>\n(&#8216;suggestion&#8217;, &#8216;Suggestion&#8217;),<br>\n)<\/p>\n<p>class ContactForm(forms.Form):<br>\ntopic = forms.ChoiceField(choices=TOPIC_CHOICES)<br>\nmessage = forms.CharField()<br>\nsender = forms.EmailField(required=False)<\/p>\n<p>\u201cNew\u201d Forms? What? &#8211; When Django was first released to the public, it had a complicated, confusing forms system. It made producing forms far too difficult, so it was completely rewritten and is now called \u201cnewforms.\u201d However, there\u2019s still a fair amount of code that depends on the \u201cold\u201d form system, so for the time being Django ships with two form packages.<br>\nAs we write this book, Django\u2019s old form system is still available as django.forms and the new form package as django.newforms. At some point that will change and django.forms will point to the new form package. However, to make sure the examples in this book work as widely as possible, all the examples will refer to django.newforms.<\/p>\n<p>A Django form is a subclass of django.newforms.Form, just as a Django model is a subclass of django.db.models.Model. The django.newforms module also contains a number of Field classes; a full list is available in Django\u2019s documentation at http:\/\/www.djangoproject.com\/documentation\/0.96\/newforms\/.<\/p>\n<p>Our ContactForm consists of three fields: a topic, which is a choice among three options; a message, which is a character field; and a sender, which is an email field and is optional (because even anonymous feedback can be useful). There are a number of other field types available, and you can write your own if they don\u2019t cover your needs.<\/p>\n<p>The form object itself knows how to do a number of useful things. It can validate a collection of data, it can generate its own HTML \u201cwidgets,\u201d it can construct a set of useful error messages and, if we\u2019re feeling lazy, it can even draw the entire form for us. Let\u2019s hook it into a view and see it in action. In views.py:<\/p>\n<p>from django.db.models import Q<br>\nfrom django.shortcuts import render_to_response<br>\nfrom models import Book<br>\nfrom forms import ContactForm<\/p>\n<p>def search(request):<br>\nquery = request.GET.get(&#8216;q&#8217;, &#8221;)<br>\nif query:<br>\nqset = (<br>\nQ(title__icontains=query) |<br>\nQ(authors__first_name__icontains=query) |<br>\nQ(authors__last_name__icontains=query)<br>\n)<br>\nresults = Book.objects.filter(qset).distinct()<br>\nelse:<br>\nresults = []\nreturn render_to_response(&#8220;books\/search.html&#8221;, {<br>\n&#8220;results&#8221;: results,<br>\n&#8220;query&#8221;: query<br>\n})<\/p>\n<p>def contact(request):<br>\nform = ContactForm()<br>\nreturn render_to_response(&#8216;contact.html&#8217;, {&#8216;form&#8217;: form})<br>\nand in contact.html:<\/p>\n<p>&lt;!DOCTYPE HTML PUBLIC &#8220;-\/\/W3C\/\/DTD HTML 4.01\/\/EN&#8221;&gt;<br>\n&lt;html lang=&#8221;en&#8221;&gt;<br>\n&lt;head&gt;<br>\n&lt;title&gt;Contact us&lt;\/title&gt;<br>\n&lt;\/head&gt;<br>\n&lt;body&gt;<br>\n&lt;h1&gt;Contact us&lt;\/h1&gt;<br>\n&lt;form action=&#8221;.&#8221; method=&#8221;POST&#8221;&gt;<br>\n&lt;table&gt;<br>\n{{ form.as_table }}<br>\n&lt;\/table&gt;<br>\n&lt;p&gt;&lt;input type=&#8221;submit&#8221; value=&#8221;Submit&#8221;&gt;&lt;\/p&gt;<br>\n&lt;\/form&gt;<br>\n&lt;\/body&gt;<br>\n&lt;\/html&gt;<\/p>\n<p>The most interesting line here is {{ form.as_table }}. form is our ContactForm instance, as passed to render_to_response. as_table is a method on that object that renders the form as a sequence of table rows (as_ul and as_p can also be used). The generated HTML looks like this:<\/p>\n<p>&lt;tr&gt;<br>\n&lt;th&gt;&lt;label for=&#8221;id_topic&#8221;&gt;Topic:&lt;\/label&gt;&lt;\/th&gt;<br>\n&lt;td&gt;<br>\n&lt;select name=&#8221;topic&#8221; id=&#8221;id_topic&#8221;&gt;<br>\n&lt;option value=&#8221;general&#8221;&gt;General enquiry&lt;\/option&gt;<br>\n&lt;option value=&#8221;bug&#8221;&gt;Bug report&lt;\/option&gt;<br>\n&lt;option value=&#8221;suggestion&#8221;&gt;Suggestion&lt;\/option&gt;<br>\n&lt;\/select&gt;<br>\n&lt;\/td&gt;<br>\n&lt;\/tr&gt;<br>\n&lt;tr&gt;<br>\n&lt;th&gt;&lt;label for=&#8221;id_message&#8221;&gt;Message:&lt;\/label&gt;&lt;\/th&gt;<br>\n&lt;td&gt;&lt;input type=&#8221;text&#8221; name=&#8221;message&#8221; id=&#8221;id_message&#8221; \/&gt;&lt;\/td&gt;<br>\n&lt;\/tr&gt;<br>\n&lt;tr&gt;<br>\n&lt;th&gt;&lt;label for=&#8221;id_sender&#8221;&gt;Sender:&lt;\/label&gt;&lt;\/th&gt;<br>\n&lt;td&gt;&lt;input type=&#8221;text&#8221; name=&#8221;sender&#8221; id=&#8221;id_sender&#8221; \/&gt;&lt;\/td&gt;<br>\n&lt;\/tr&gt;<\/p>\n<p>Note that the &lt;table&gt; and &lt;form&gt; tags are not included; you need to define those yourself in the template, which gives you control over how the form behaves when it is submitted. Label elements are included, making forms accessible out of the box.<\/p>\n<p>Our form is currently using a &lt;input type=&#8221;text&#8221;&gt; widget for the message field. We don\u2019t want to restrict our users to a single line of text, so we\u2019ll swap in a &lt;textarea&gt; widget instead:<\/p>\n<p>class ContactForm(forms.Form):<br>\ntopic = forms.ChoiceField(choices=TOPIC_CHOICES)<br>\nmessage = forms.CharField(widget=forms.Textarea())<br>\nsender = forms.EmailField(required=False)<\/p>\n<p>The forms framework separates out the presentation logic for each field into a set of widgets. Each field type has a default widget, but you can easily override the default, or provide a custom widget of your own. At the moment, submitting the form doesn\u2019t actually do anything. Let\u2019s hook in our validation rules:<\/p>\n<p>def contact(request):<br>\nif request.method == &#8216;POST&#8217;:<br>\nform = ContactForm(request.POST)<br>\nelse:<br>\nform = ContactForm()<br>\nreturn render_to_response(&#8216;contact.html&#8217;, {&#8216;form&#8217;: form})<\/p>\n<p>A form instance can be in one of two states: bound or unbound. A bound instance is constructed with a dictionary (or dictionary-like object) and knows how to validate and redisplay the data from it. An unbound form has no data associated with it and simply knows how to display itself.<br>\nTry clicking Submit on the blank form. The page should redisplay, showing a validation error that informs us that our message field is required.<\/p>\n<p>Try entering an invalid email address as well. The EmailField knows how to validate email addresses, at least to a reasonable level of doubt.<\/p>\n<p><strong>Setting Initial Data<\/strong> &#8211; Passing data directly to the form constructor binds that data and indicates that validation should be performed. Often, though, we need to display an initial form with some of the fields prefilled \u2014 for example, an \u201cedit\u201d form. We can do this with the initial keyword argument:<br>\nform = CommentForm(initial={&#8216;sender&#8217;: &#8216;user@example.com&#8217;})<br>\nIf our form will always use the same default values, we can configure them in the form definition itself:<\/p>\n<p>message = forms.CharField(widget=forms.Textarea(),<br>\ninitial=&#8221;Replace with your feedback&#8221;)<\/p>\n\n\n<p><a href=\"https:\/\/www.vskills.in\/certification\/tutorial\/certified-django-developer\/\" target=\"_blank\" rel=\"noreferrer noopener\">Back to Tutorial<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Forms can often be a major cause of frustration for the users of your site. Let\u2019s consider the behavior of a hypothetical perfect form: It should ask the user for some information, obviously. Accessibility and usability matter here, so smart use of the HTML &lt;label&gt; element and useful contextual help are important. The submitted data&#8230;<\/p>\n","protected":false},"author":1,"featured_media":0,"parent":0,"menu_order":0,"comment_status":"closed","ping_status":"closed","template":"","meta":{"footnotes":""},"categories":[8655],"tags":[8770],"class_list":["post-75671","page","type-page","status-publish","hentry","category-django-web-development","tag-the-perfect-form"],"acf":[],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v24.5 - https:\/\/yoast.com\/wordpress\/plugins\/seo\/ -->\n<title>The \u201cPerfect Form\u201d - Tutorial<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"The \u201cPerfect Form\u201d - Tutorial\" \/>\n<meta property=\"og:description\" content=\"Forms can often be a major cause of frustration for the users of your site. Let\u2019s consider the behavior of a hypothetical perfect form: It should ask the user for some information, obviously. Accessibility and usability matter here, so smart use of the HTML &lt;label&gt; element and useful contextual help are important. The submitted data...\" \/>\n<meta property=\"og:url\" content=\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/\" \/>\n<meta property=\"og:site_name\" content=\"Tutorial\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/vskills.in\/\" \/>\n<meta property=\"article:modified_time\" content=\"2024-04-12T08:47:14+00:00\" \/>\n<meta name=\"twitter:label1\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data1\" content=\"7 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"WebPage\",\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/\",\"url\":\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/\",\"name\":\"The \u201cPerfect Form\u201d - Tutorial\",\"isPartOf\":{\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/#website\"},\"datePublished\":\"2020-01-20T05:58:57+00:00\",\"dateModified\":\"2024-04-12T08:47:14+00:00\",\"breadcrumb\":{\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/\"]}]},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/www.vskills.in\/certification\/tutorial\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"The \u201cPerfect Form\u201d\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/#website\",\"url\":\"https:\/\/www.vskills.in\/certification\/tutorial\/\",\"name\":\"Tutorial\",\"description\":\"Vskills - A initiative in elearning and certification\",\"publisher\":{\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/www.vskills.in\/certification\/tutorial\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/#organization\",\"name\":\"Vskills\",\"url\":\"https:\/\/www.vskills.in\/certification\/tutorial\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/#\/schema\/logo\/image\/\",\"url\":\"https:\/\/www.vskills.in\/certification\/tutorial\/wp-content\/uploads\/2017\/07\/vskills-min-logo.jpg\",\"contentUrl\":\"https:\/\/www.vskills.in\/certification\/tutorial\/wp-content\/uploads\/2017\/07\/vskills-min-logo.jpg\",\"width\":73,\"height\":55,\"caption\":\"Vskills\"},\"image\":{\"@id\":\"https:\/\/www.vskills.in\/certification\/tutorial\/#\/schema\/logo\/image\/\"},\"sameAs\":[\"https:\/\/www.facebook.com\/vskills.in\/\",\"https:\/\/x.com\/vskills_in\",\"https:\/\/www.linkedin.com\/company-beta\/1371554\/\",\"https:\/\/www.youtube.com\/channel\/UCMWnscxPwRF_PqXo9B7q_Tw\"]}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"The \u201cPerfect Form\u201d - Tutorial","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/","og_locale":"en_US","og_type":"article","og_title":"The \u201cPerfect Form\u201d - Tutorial","og_description":"Forms can often be a major cause of frustration for the users of your site. Let\u2019s consider the behavior of a hypothetical perfect form: It should ask the user for some information, obviously. Accessibility and usability matter here, so smart use of the HTML &lt;label&gt; element and useful contextual help are important. The submitted data...","og_url":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/","og_site_name":"Tutorial","article_publisher":"https:\/\/www.facebook.com\/vskills.in\/","article_modified_time":"2024-04-12T08:47:14+00:00","twitter_misc":{"Est. reading time":"7 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"WebPage","@id":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/","url":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/","name":"The \u201cPerfect Form\u201d - Tutorial","isPartOf":{"@id":"https:\/\/www.vskills.in\/certification\/tutorial\/#website"},"datePublished":"2020-01-20T05:58:57+00:00","dateModified":"2024-04-12T08:47:14+00:00","breadcrumb":{"@id":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/"]}]},{"@type":"BreadcrumbList","@id":"https:\/\/www.vskills.in\/certification\/tutorial\/the-perfect-form\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/www.vskills.in\/certification\/tutorial\/"},{"@type":"ListItem","position":2,"name":"The \u201cPerfect Form\u201d"}]},{"@type":"WebSite","@id":"https:\/\/www.vskills.in\/certification\/tutorial\/#website","url":"https:\/\/www.vskills.in\/certification\/tutorial\/","name":"Tutorial","description":"Vskills - A initiative in elearning and certification","publisher":{"@id":"https:\/\/www.vskills.in\/certification\/tutorial\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.vskills.in\/certification\/tutorial\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/www.vskills.in\/certification\/tutorial\/#organization","name":"Vskills","url":"https:\/\/www.vskills.in\/certification\/tutorial\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/www.vskills.in\/certification\/tutorial\/#\/schema\/logo\/image\/","url":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-content\/uploads\/2017\/07\/vskills-min-logo.jpg","contentUrl":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-content\/uploads\/2017\/07\/vskills-min-logo.jpg","width":73,"height":55,"caption":"Vskills"},"image":{"@id":"https:\/\/www.vskills.in\/certification\/tutorial\/#\/schema\/logo\/image\/"},"sameAs":["https:\/\/www.facebook.com\/vskills.in\/","https:\/\/x.com\/vskills_in","https:\/\/www.linkedin.com\/company-beta\/1371554\/","https:\/\/www.youtube.com\/channel\/UCMWnscxPwRF_PqXo9B7q_Tw"]}]}},"_links":{"self":[{"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/pages\/75671","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/comments?post=75671"}],"version-history":[{"count":4,"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/pages\/75671\/revisions"}],"predecessor-version":[{"id":83350,"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/pages\/75671\/revisions\/83350"}],"wp:attachment":[{"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/media?parent=75671"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/categories?post=75671"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.vskills.in\/certification\/tutorial\/wp-json\/wp\/v2\/tags?post=75671"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}