Programación Back-End

Unidad 2: Framework Back-End

Formularios Django

Redactado por Criz
Publicado el 4 de junio de 2024 a las 23:00
Última actualización el 4 de junio de 2024 a las 23:00

Acciones rapidas
Editar
Siguiente
Previo

Formularios

Los formularios nos dan una forma de recibir datos del usuario. Son útiles y muy fáciles de crear.

Los hay de dos tipos:

  1. Formulario de modelo: Básicamente hereda los campos de un modelo.
  2. Formulario simple: Un formulario en el que definimos sus campos.

Los formularios son creados con Python y luego Django se encarga de transformarlos a HTML.
Estos formularios son creados en un archivo forms.py dentro de la carpeta de la aplicación que los usara.

Creando formularios

Primero, creamos un archivo dentro de nuestra aplicación llamado forms.py, tal que quede tienda/forms.py.

Creando un formulario desde un Modelo

Para heredar los campos de un modelo, primero importamos forms y ModelForm dentro de forms.py:

1
2
from django import forms # lo usaremos mas adelante
from django.forms import ModelForm

Luego debemos importar el modelo a nuestro forms.py:

1
2
...
from .models import Producto

Ahora, los formularios en Django son declarados como clases Python:

1
2
3
4
5
6
7
8
#                     👇 heredamos los metodos de ModelForm. necesario para heredar los campos del modelo
class ProductoForm(ModelForm):
    #      👇 en Meta declaramos la configuracion del formulario
    class Meta:
        #          👇 indicamos el modelo que queremos heredar
        model = Producto
        #        👇 indicamos los campos que queremos mostrar
        fields = ["nombre", "descripcion", "stock", "precio"]

Y ya está. Si, literal.

Formulario a template

Ahora vamos a crear una nueva template templates/tienda/crud.html para poder organizar todo y que quede bien:

1
2
3
4
5
6
7
{% extends 'base.html' %}

{% block title %}CRUD{% endblock %}

{% block content %}
<div class="container"></div>
{% endblock %}

Ahora, dentro del bloque content mostramos el formulario:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
...
<!-- vemos si hay un formulario -->
{% if form %}
    <form action="" method="post">
        <!-- csrf_token es obligatorio, es para evitar un tipo de ataque con su mismo nombre -->
        {% csrf_token %}
        <!-- evaluamos la variable form -->
        {{ form }}
        <button type="submit">Submit</button>
    </form>
{% endif %}
...

CSRF es un ataque peligroso en el cual un atacante atacar a un usuario cuya sesión se encuentra activa en un sitio, el sitio confía en él, pero el usuario no sabe que ejecuta código malicioso con sus credenciales.
La protección contra CSRF se puede desactivar, pero no se recomienda.
Mas información sobre el CSRF puede ser encontrada en https://owasp.org/www-community/attacks/csrf#overview

Creamos la vista

En views.py creamos una nueva vista:

1
2
3
def crear(request):
    formulario = ProductoForm()
    return render(request, "tienda/crud.html", {"form":formulario})

Obviamente, también necesitamos importar el ProductoForm desde forms.py:

1
from .forms import ProductoForm

Creamos la ruta

Y ahora registramos la ruta en urls.py:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
urlpatterns = [
    ...
    # 📌 Esta ruta se llama xq django piensa que 'crear' en la url es un slug de un producto, por eso podemos moverla al final.
    # path('<slug:uid>/', app.producto, name="producto"),
    # O, mejor usamos la recomendacion, usar sub-rutas para evitar eso. quedando asi:
    path('producto/<slug:uid>/', app.producto, name="producto"),
    # si has usado el tag 'url' en las templates, no deberas hacer nada mas.

    # 👇 definimos la ruta
    path('crear/', app.crear, name="crear"),
]

TEST TIME

Si todo va bien, al dirigirte a http://127.0.0.1:8000/crear/ deberías ver algo así:

Estilizando formularios

Como puedes observar, el formulario es feo. Esto es ya que Django no sabe de la existencia de Boostrap.
Por ello, debemos editar el widget asociado a los campos para poder aplicar estilos y atributos.

widgets

Un campo es un objeto con un tipo de dato asociado, este objeto es nada más que un input, el cual posee atributos, y para acceder a estos, se usan los widgets.
Para editarlos, vamos a forms.py y modificamos los widgets de cada campo:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
class ProductoForm(ModelForm):
    class Meta:
        model = Producto
        fields = ["nombre", "descripcion", "stock", "precio"]
        # 👇 nos permite ocultar los textos de ayuda de los inputs
        #labels = {
            #     👇 nombre del campo
            # '<field>' : '',
            #        👆 texto de ayuda
        #}
        # en widgets se encuentran todos los fiels que hayamos declarado en 'fields = [...]'
        widgets = {
            #               👇 podemos sobreescribir el tipo de input html
            "nombre": forms.TextInput(
                attrs={
                    #              👇 estilo de Boostrap
                    "class": "form-control"
                }
            ),
            #                       👇 el textarea va con el campo TextField del modelo
            "descripcion": forms.Textarea(
                attrs={
                    "rows": 5, # 👈 indicamos que tan largo debe ser el campo
                    "class": "form-control"
                }
            ),
            "stock": forms.NumberInput(
                attrs={
                    "class": "form-control"
                }
            ),
            "precio": forms.NumberInput(
                attrs={
                    "class": "form-control"
                }
            ),
        }

Ahora, al actualizar la página, podremos ver los cambios.

Recomendación: Investiga sobre una librería de Python que se especializa en los formularios de Django.
django-crispy-forms, puedes encontrar su documentación en https://django-crispy-forms.readthedocs.io/en/latest/.
Esta librería es un MUST HAVE (debes tener) en tu proyecto Django.
Tópicos importantes:

  • crispy: el tag para renderizar el formulario.
  • layouts: para estilizado y lindura de tu formulario.

En este curso, no usaremos ni enseñare a usar django-crispy-forms.

Divide y conquistaras

El próximo capitulo continuaremos con los formularios.


Siguiente
Previo