Custom Forms

Learn via video courses
Topics Covered

Overview

In Django, a form is a way to create and process HTML forms. It provides a convenient way to represent and validate user input and can be used to render forms in a template.

Custom forms in Django are forms that you create yourself, rather than using Django's built-in form classes. This can be useful if you need to create a form with specific fields or functionality that is not provided by the built-in form classes.

Working With Forms

Forms are a common feature of websites and applications that allow users to input data or interact with the interface in some way. They are typically used to collect information from users, such as contact information, feedback, or responses to questions. Forms can be created using HTML, which is the standard markup language for creating web pages. Here is an example of a simple form that collects a user's name and email address:

This form consists of two input fields for the user's name and email address, as well as a submit button. When the user fills out the form and clicks the submit button, the form data is sent to the server for processing.

Many different types of form elements can be used, such as text fields, checkboxes, radio buttons, and select menus.

HTML Forms

HTML forms are used to collect data from users on a website or web application. They are created using the <form> element, which encloses a series of input fields, buttons, and other form elements. Example: Here is a simple HTML form that collects a user's name and email address:

The form consists of two input fields for the user's name and email address, as well as a submit button. The type attribute of the input element specifies the type of input field, and the name attribute specifies the name of the field. The submit button has a type attribute of submit, which indicates that it is used to submit the form data.

To process the form data, you will typically need to specify an action attribute in the <form> element, which specifies the URL of the server-side script that will handle the form submission. You can also use the method attribute to specify whether the form data should be submitted using the HTTP GET or POST method.

GET and POST

In HTML forms, the method attribute specifies the HTTP method used to submit the form data to the server. The two most common methods are GET and POST.

The GET method sends the form data as part of the URL, appended as query parameters. This is useful for forms that do not contain sensitive information and do not need to be secure, as the data is visible in the URL and is not encrypted.

The POST method, on the other hand, sends the form data in the request body, which is not visible in the URL and is encrypted if the website uses HTTPS. This is more secure and is typically used for forms that contain sensitive information or that make changes to the server, such as submitting a password or updating a database.

Here is an example of a form that uses the GET method:

When the user submits this form, the form data is appended to the URL as query parameters, like this:

Here is an example of a form that uses the POST method:

When the user submits this form, the form data is sent in the request body and is not visible in the URL.

It is important to choose the appropriate method for your form based on the type of data you are collecting and the level of security you need. In general, the GET method is suitable for forms that do not contain sensitive information and do not make any changes to the server, while the POST method is more appropriate for forms that contain sensitive information or that make changes to the server.

Django’s Role In Forms

Django's forms framework has several advantages that make it a useful tool for working with forms in your web applications. Some of the main benefits of using Django's forms framework include:

  • Validation: Django's forms framework includes built-in validation logic that can be used to ensure that form data is valid before it is submitted.
  • Security: Django's forms framework includes several security features, such as CSRF protection and form rendering helpers that help prevent cross-site scripting attacks.
  • Reusability Django's forms framework allows you to define form classes that can be reused across multiple views and templates.
  • Integration with the Django ORM: Django's forms framework is tightly integrated with the Django ORM, which makes it easy to create forms that can create or update database objects.

Large sections of jobs can be streamlined and automated with Django's form functionality. Additionally, it can be done more securely with custom forms in Django functionality than it would be for the majority of programmers to do with their code.

Three different tasks associated with forms are handled by Django:

  • Transforming and organizing data to get it suitable for rendering
  • Constructing HTML forms for data
  • collection, receiving, and handling client-submitted forms and data.

The Django Form Class

Custom forms in Django have a form class (Python class) that defines the fields and behavior of a form. Form classes are used to handle user input and can be used to generate HTML forms for rendering in a template. To create a form class in Django, you will need to subclass forms.Form or forms.ModelForm and define the fields that the form should include.

Example:

This form class defines three fields: name, email, and message. Each field is represented by a form field class, such as CharField or EmailField, which specifies the type of data that the field should accept.

Instantiating, Processing, and Rendering Forms

Here are the steps to instantiate, process, and render custom forms in Django:

  1. Create a form class and define the fields that the form should include.
  2. In a view, create an instance of the form class and pass any necessary arguments.
  3. If the request method is POST, validate the user input using the form.is_valid() method. If the form is valid, process the form data. If the form is invalid, render the form template with the form instance and any error messages.
  4. If the request method is GET, render the form template with the form instance.
  5. In the template, use the {% form %} template tag to render the form, and use the {% field %} template tag to render each form field. Django also provides a jinja library to use in templates.

Further in this article, you will see how to implement these steps to build forms in Django.

Building A Form

The Work That Needs To Be Done

To build a form in Django, you will need:

  1. Django installed on your system. You can install Django using pip: pip install Django
  2. A Django project and app setup. You can create a new Django project and app using the Django-admistart project t and python manage.py startapp commands.
  3. Familiarity with the Django forms API. You should have a basic understanding of how to create form classes and render forms in templates.
  4. A model to work with if you are using a model form.

Once you have these prerequisites in place, you can start building your form by defining a form class and specifying the fields that the form should include. You can then use the form in a view to handle user input and render the form in a template.

Building A Form In Django

To build custom forms in Django, you will need to do the following steps:

  • Create a form class: In your forms.py file, create a class that inherits from forms.Form or forms.ModelForm, depending on whether you want to create a form for a model or a standalone form.
  • Define the form fields: Use the fields attribute to specify the fields that you want to include in your form. If you are using a ModelForm, Django will automatically generate the form fields based on the model fields.
  • Render the form in a template: In your template, use the {% csrf_token %} template tag to protect against cross-site request forgery (CSRF) attacks, and then use the {% form %} template tag to render the form. The Form Class To build custom forms in Django, you will need to use the Form class or the ModelForm class. The Form class is used to create a form from scratch, while the ModelForm class is used to create a form based on a Django model.

Example:

This form has three fields: name, email, and message. The CharField and EmailField are built-in field types, while the widget argument is used to specify the HTML widget to use for the field. In this case, we are using a Textarea widget for the message field.

The View

To use this form in a view, you will need to import the form and create a view function that handles the form submission.

Here is an example of a view function that displays and processes the form:

In this view, we check the request method to determine if the form has been submitted. If the request method is POST, we create a form instance with the submitted data and check if the form is valid. If the form is valid, we can process the data and redirect the user to a success page. If the request method is GET, we create an empty form and render the template with the form context.

The Template

To display the form in a template, you will need to use Django's template language to render the form fields and handle the form submission.

Here is an example of how to render the form in a template:

In this template, we use the {% csrf_token %} template tag to protect against cross-site request forgery attacks. We also use the {{ form.as_p }} template tag to render the form fields as <p> elements. Finally, we include a submit button to allow the user to submit the form.

More About Django Form Classes

Bound And Unbound Form Instances

In Django, a form instance is considered "bound" if it contains data that has been submitted by the user. An "unbound" form instance does not contain any data.

When you create a form instance with submitted data, the form is bound to that data. For example, if you create a form instance using the POST data from a form submission, the form will be bound to that data:

If you create a form instance without any data, the form will be unbound:

A bound form instance has access to the submitted data through the form.data attribute. You can use this attribute to access the raw data, or you can use the form.cleaned_data attribute to access the data after it has been validated and cleaned.

An unbound form instance does not have access to any data, but you can still use it to render the form fields in a template. For example, you can use the {{ form.as_p }} template tag to render the form fields as <p> elements:

More On Fields

Custom forms in Django, has form fields that are represented by instances of the Field class. You can use the built-in field types, such as CharField, EmailField, and DateField, or you can create custom field types by subclassing the Field class. Example:

In this example, we have a CharField for the name and message fields, an EmailField for the email field, a ChoiceField for the subject field, and a BooleanField for the cc_myself field.

The CharField and EmailField are simple text fields, while the ChoiceField allows the user to select a value from a predefined list of choices. The BooleanField is a checkbox field that allows the user to select a true or false value.

You can customize the behavior of a field by using field arguments. For example, you can use the required argument to specify if a field is required, or you can use the widget argument to specify the HTML widget to use for the field.

Widgets

In Django, widgets are used to control the HTML representation of form fields. You can specify the widget to use for a field by using the widget argument when you define the field.

Django comes with a number of built-in widgets, including TextInput, PasswordInput, Textarea, and Select. You can also create custom widgets by subclassing the Widget class.

Field Data

In Django, you can access the data for a form field in several ways.

If the form is bound to submsubmita, you can access the raw data for a field through the form.data attribute. For example, to access the raw data for the name field in a bound form, you can use form.data['name']. It is generally a good idea to use the form.cleaned_data attribute to access the data for a field, as this attribute contains the data after it has been validated and cleaned. For example, to access the cleaned data for the name field in a bound form, you can use form.cleaned_data['name'].

If the form is unbound, you can use the form.initial attribute to access the initial data for a field. For example, to access the initial data for the name field in an unbound form, you can use form.initial['name']. You can also access the field instance for a field through the form.fields attribute. For example, to access the field instance for the name field, you can use form.fields['name'].

Example:

Working With Form Templates

Reusable form Templates

To create reusable form templates in Django, you can use the include template tag and pass it the name of the form template you want to include. For example, let's say you have a form template named _form.html that you want to reuse in multiple places in your Django application. You can include this form template in another template using the include tag like this:

You can also pass variables to the included template using the clause. Example:

This will pass the form variable to the included template, which can then access it using the form variable name.

You can also use the extends template tag to create a base template that includes the form template and then extend that base template in other templates. This can be useful if you want to define a common layout for pages that use the form template.

For example, let's say you have a base template named base.html that includes the form template, and you want to create a page template that extends base.html and overrides some of the content. You can do this like this:

This will render the form template in the context of the base.html template, using the layout defined in base.html and the content defined in the page template.

Form Rendering Options

There are several ways to render a form in Django. Here are a few options:

  • Render the form manually: You can render custom forms in django manually by iterating over the form's fields and rendering them one by one. This is a good option if you need complete control over the form's layout and HTML.
  • Use Django's built-in form rendering functions: Django provides several built-in functions for rendering forms, such as {{ form.as_p }}, {{ form.as_table }}, and {{ form.as_ul }}. These functions render the form's fields as a series of <p>, <table>, or <ul> elements, respectively.
  • Use Django's form rendering helpers: Django also provides a set of form rendering helpers that make it easier to customize the rendering of a form. You can use these helpers to specify the HTML tags, CSS classes, and other attributes for the form and its fields.
  • Use a form template: Another option is to create a form template that defines the layout and styling for the form. You can then include this template in your views and pass it to the form object as a context variable. This allows you to reuse the form template across multiple views and keep the form rendering logic separate from the view code.

Which option you choose will depend on your specific needs and preferences. In most cases, using a form template or Django's built-in form rendering functions will be the easiest and most efficient approach.

Rendering Fields Manually

To render a form's fields manually in Django, you can iterate over the form's fields in a template and render each field individually.

Example:

This template code will render the form fields as a series of div elements, with the label and field widget for each field and a help text below the field, if one is provided.

You can customize the rendering of each field by accessing its attributes and methods. For example, you can access the field's label, widget, and help text using the label, field.widget, and help_text attributes, respectively. You can also use the label_tag method to render the field's label as an HTML label element.

By rendering the form fields manually, you have complete control over the HTML layout and styling of the form. However, this approach can be more time-consuming and error-prone than using Django's built-in form rendering functions or form templates.

Rendering Form Error Messages

To render form error messages in Django, you can use the {{ form.errors }} template variable, which contains a list of all the form's errors.

Example:

This template code will render the form errors as a list of li elements inside a div element with the alert and alert-danger classes.

You can customize the rendering of the form errors by modifying the HTML and CSS as needed. For example, you can use different classes or styles for the alert container and list items, or you can use a different HTML element to display the errors.

Note that you should only display form errors after the form has been submitted and validated. You can use the {{ form.is_valid }} template variable to check if the form is valid before displaying the errors.

Looping Over the Form’s Fields

To loop over a form's fields in Django, you can use the template tag and pass it to the form object.

Example:

This template code will iterate over each field in the form and render it as a div element with the label and field widget inside. If the field has a help text, it will also be rendered as a p element below the field.

You can access the field's attributes and methods inside the loop to customize the rendering of each field. For example, you can use the label_tag method to render the field's label as an HTML label element, or you can access the field's help_text attribute to display a help message below the field.

You can also use the for template tag to loop over the form's errors and display them to the user.

Example:

This template code will iterate over each field's errors and render them as p elements with the error-message class. It will also display any non-field errors that are not associated with a specific field.

Looping Over Hidden And Visible Fields

To loop over hidden and visible fields separately in Django, you can use the form.hidden_fields and form.visible_fields template variables, which contain lists of the form's hidden and visible fields, respectively.

Example:

Note that the form.hidden_fields and form.visible_fields template variables are only available in Django 2.1 and later. In earlier versions of Django, you can use the form.field.is_hidden attribute to determine if a field is hidden or visible.

Conclusion

Here are a few key points to consider when working with custom forms in Django:

  • Forms are an important part of any web application, as they allow you to collect and validate user input.
  • Django provides several built-in form fields and widgets that you can use to build custom forms. You can also create custom form fields and widgets to meet specific needs.
  • You can use Django's form validation system to ensure that user input is valid and consistent. This includes validating individual fields, as well as checking for errors across the form as a whole.
  • There are several ways to render a form in Django, including manually rendering the fields, using Django's built-in form rendering functions, using Django's form rendering helpers, or using a form template.
  • You can customize the rendering of a form and its fields by accessing their attributes and methods, or by using a form template to define the form's layout and styling.
  • You can use the form.hidden_fields and form.visible_fields template variables to loop over the form's hidden and visible fields separately, or you can use the form.field.is_hidden attribute to determine if a field is hidden or visible.

By following these best practices, you can create custom forms that are easy to use, maintain, and extend in your Django applications.