En esta página:
Demo Github
Y llegamos a la última parte de este tutorial, que consta en general de 5 partes.
En la penúltima o cuarta parte hicimos uso de las vistas genéricas nativas del framework Django para poder hacer que nuestros datos interactúen con las vistas HTML.
En esta última vamos a realizar ciertas tareas que forman parte del tutorial llamado Como Crear Un CRUD con Django, vamos con ello.
Partes
En la cuarta parte de este tutorial creamos 4 archivos HTML dentro de nuestra carpeta templates
Estos archivos son actualizar.html, crear.html, detalles.html e index.html y ahora los vamos a usar para las vistas del usuario final.
Vistas HTML (Bootstrap 5)
Antes de poder crear las vistas HTML debemos de instanciar la librería o core de Bootstrap 5 junto a su archivo de estilos CSS, todo esto debemos hacerlo en cada archivo HTML de nuestro Sistema CRUD, lo colocamos entre las etiquetas <head></head>:
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 |
<!doctype html> <html lang="es"> <head> <title>Como Crear Un CRUD con Django 5 </title> {# Cargamos la librería #} {% load django_bootstrap5 %} {# CSS Bootstrap #} {% bootstrap_css %} {# Widget Tweaks #} {% load widget_tweaks %} {# Archivos #} {% load static %} </head> <body> ... ... ... |
Luego de instanciar Bootstrap 5 correctamente, ya podemos crear las vistas HTML para las operaciones CRUD.
Página Principal (Listado de Todos los Registros )
Acá listamos todos los jugos en una tabla HTML de Bootstrap 5, abro el archivo index.html y agrego lo siguiente:
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 38 39 40 41 42 43 44 45 46 47 |
<div align="left" class="btn_crear mb-3"> <a href="crear" type="button" class="btn btn-primary">Crear</a> </div> <table class="table table-striped table-hover"> <thead> <tr> <th width="35%">Nombre</th> <th>Precio</th> <th>Stock</th> <th>Imagen</th> <th>Acciones</th> </tr> </thead> <tbody> <!-- Recorremos los objetos o registros que tenemos en nuestra tabla 'jugos' y los listamos --> {% for jugo in object_list %} <tr> <td>{{ jugo.nombre }}</td> <td>{{ jugo.precio }}</td> <td>{{ jugo.stock }}</td> <td><img src="{% static 'uploads/'%}{{jugo.img}}" alt="{{jugo.nombre}}" class="img-fluid" width="7%"></td> <td> <!-- Usaremos un formulario que realizará la tarea de eliminar un registro o jugo desde la misma tabla HTML --> <form method="POST" action="eliminar/{{jugo.id}}"> {% csrf_token %} <div class="btn-group"> <!-- Creamos 3 botones que son ver, Editar y Eliminar, nos sirven para gestionar nuestros registros o jugos --> <a href="detalle/{{jugo.id}}" title="Ver" type="button" class="btn btn-success">Ver </a> <a href="editar/{{jugo.id}}" title="Editar" type="button" class="btn btn-primary">Editar </a> <button class="btn btn-danger" onclick="return eliminar();" type="submit"> Eliminar </button> </div> </form> </td> </tr> {% endfor %} </tbody> </table> |
En el código anterior, puedes fijarte que antes de la tabla, he colocado un botón Crear, con el creamos un nuevo registro en la base de datos:
1 2 3 4 5 |
<div align="left" class="btn_crear mb-3"> <a href="crear" type="button" class="btn btn-primary">Crear</a> </div> |
Con ello tenemos nuestra vista principal (index.html) con el listado respectivo de los jugos o registros.
Recuerda que cada ves agreguemos un nuevo registro a la base de datos, este aparecerá en la tabla HTML y automáticamente el sistema le asigna una tira de botones que son Ver, Editar y Eliminar:
Ya tenemos la vista principal o main del sistema CRUD, ahora pasemos a crear las vistas especificas para las tarea CRUD.
Crear (Create)
Mediante esta vista podemos crear un nuevo registro o jugo.
Abro el archivo crear.html el cual lo creamos en la tercera parte de este tutorial, este archivo se encuentra dentro de la carpeta templates y en el agrego el siguiente formulario:
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 |
<form method="post" enctype="multipart/form-data"> # Pasamos el 'csrf_token' de seguridad para poder crear un nuevo registro {% csrf_token %} <!-- {{ form.as_p }} --> <div class="form-group mb-2"> <label for="nombre" class="txt_negrita">Nombre</label> {{ form.nombre|add_class:"form-control" }} <!-- Usamos la librería 'widget_tweaks' para crear esta caja de texto --> </div> <div class="form-group mb-2"> <label for="precio" class="txt_negrita">Precio</label> {{ form.precio|add_class:"form-control" }} <!-- Usamos la librería 'widget_tweaks' para crear esta caja de texto --> </div> <div class="form-group mb-2"> <label for="stock" class="txt_negrita">Stock</label> {{ form.stock|add_class:"form-control" }} <!-- Usamos la librería 'widget_tweaks' para crear esta caja de texto --> </div> <div class="form-group mb-2"> <label for="img" class="txt_negrita">Imagen</label> {{ form.img|add_class:"form-control mb-3" }} <!-- Usamos la librería 'widget_tweaks' para crear esta caja de texto --> </div> <button type="submit" class="btn btn-primary">Aceptar</button> <a href="./" type="submit" class="btn btn-primary">Cancelar</a> </form> |
En el código anterior del archivo crear.html estamos usando la librería widget_tweaks que instale en la Parte 4 de este tutorial,
Esta librería nos permite gestionar nuestros formularios creados mediante Vistas Genéricas de Django.
Con ello tenemos nuestra vista crear.html con el formulario para ingresar un nuevo jugo o registro:
Pasemos a crear la vista para leer los detalles de un registro.
Leer (Read)
Esta vista la usaremos para mostrar los detalles de un registro de manera independiente, cada ves que el usuario presione el botón Ver que se encuentra en la columna Acciones al lado de un determinado registro en la tabla HTML del archivo index.html
Agrego el siguiente código HTML al archivo detalles.html que se encuentra en la carpeta templates, con este código imprimimos los objetos o datos con la información de un registro específico:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
<h4>Detalles</h4> <p><span class="txt_negrita">Nombre:</span> <br> {{object.nombre}}</p> <p><span class="txt_negrita">Precio:</span> <br> {{object.precio}}</p> <p><span class="txt_negrita">Stock:</span> <br> {{object.stock}}</p> <p><span class="txt_negrita">Imagen:</span> <br> <img src="{% static 'uploads/'%}{{object.img}}" alt="{{object.nombre}}" class="img-fluid"> </p> <p><span class="txt_negrita">Creado:</span> <br> {{object.created_at}}</p> <p><span class="txt_negrita">Actualizado:</span> <br> {{object.updated_at}}</p> <!-- Botón para volver a la vista principal (Home) --> <a href="../" type="submit" class="btn btn-primary">Volver</a> |
El sistema envía el id del registro al archivo o template llamado detalles.html para mostrar los detalles de dicho registro, el envío de este id lo hace por la ruta jugos/detalle/<int:pk>:
1 2 3 |
path('jugos/detalle/<int:pk>', DetalleJugo.as_view(template_name = "jugos/detalles.html"), name='detalles'), |
La ruta anterior la definimos en la cuarta parte de este tutorial, específicamente dentro del archivo urls.py
Entonces con ello tenemos nuestra vista Leer con los datos de un registro determinado:
Pasemos a crear la vista para actualizar un registro.
Actualizar (Update)
Para esta vista colocaré un formulario HTML para poder editar un registro determinado.
Mostramos los valores específicos de un registro o jugo en cada campo del formulario, para que puedan ser editados.
Abrimos el archivo actualizar.html que se encuentra en la carpeta templates y agrego el siguiente código HTML:
Ahora veamos la vista HTML Eliminar, pero más que una vista es una función o tarea del sistema CRUD, veámosla mejor a continuación.
Eliminar (Delete)
Para esta vista vamos a usar el archivo index.html que se encuentra dentro de la carpeta templates, en este archivo estamos listando todos los registros o jugos de la base de datos en la vista principal.
Puedes ver en la columna Acciones, he colocado un botón que dice Eliminar. Este botón nos va a servir para eliminar un registro de la tabla jugos:
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 38 39 40 41 42 43 44 |
<table class="table table-striped table-hover"> <thead> <tr> <th width="35%">Nombre</th> <th>Precio</th> <th>Stock</th> <th>Imagen</th> <th>Acciones</th> </tr> </thead> <tbody> {% for jugo in object_list %} <tr> <td>{{ jugo.nombre }}</td> <td>{{ jugo.precio }}</td> <td>{{ jugo.stock }}</td> <td><img src="{% static 'uploads/'%}{{jugo.img}}" alt="{{jugo.nombre}}" class="img-fluid" width="7%"></td> <td> <!-- Usaremos un formulario que realizará la tarea de eliminar un registro o jugo desde la misma tabla HTML --> <form method="POST" action="eliminar/{{jugo.id}}"> {% csrf_token %} <div class="btn-group"> <a href="detalle/{{jugo.id}}" title="Ver" type="button" class="btn btn-success">Ver </a> <a href="editar/{{jugo.id}}" title="Editar" type="button" class="btn btn-primary">Editar </a> <!-- Este botón ejecuta el formulario para eliminar un registro o jugo en la Base de datos --> <button class="btn btn-danger" onclick="return eliminar();" type="submit"> Eliminar </button> </div> </form> </td> </tr> {% endfor %} </tbody> </table> |
Lo que haremos es eliminar los registros desde la misma página, no sería muy estético eliminar el registro en una nueva página HTML, salvo que tu proyecto lo requiera.
Por seguridad antes de eliminar un registro, vamos a consultar al usuario si desea eliminar un registro, dentro de nuestro botón para enviar el formulario llamamos a la función Javascript eliminar():
1 2 3 4 5 |
<button class="btn btn-danger" onclick="return eliminar();" type="submit"> Eliminar </button> |
Si el usuario hace clic en el botón Eliminar, le mostramos una alerta con el mensaje: Eliminar Producto ?
Mi función eliminar(); la he creado con Javascript y la colocamos al final antes de cerrar la etiqueta </body> de nuestro archivo HTML llamado index.html:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
<script type="text/javascript"> function eliminar() { var x = confirm("Eliminar Producto ?"); if (x) return true; else return false; } </script> </body> </html> |
Cuando el usuario haga clic en el botón Eliminar de alguno de los registros de la tabla HTML, le lanzamos la alerta para que confirme la eliminación del registro:
Mediante la alerta, impedimos que el usuario borre por error alguno de los registros.
Mensajes
Dentro del archivo index.html van a mostrarse todos los mensajes de las operaciones Crear, Eliminar y Actualizar.
Es decir después de Insertar, Eliminar o Actualizar un registro o jugo de la base de datos, mostramos un mensaje para confirmar que dicha operación ha sido realizada Correctamente.
Abrimos el archivo index.html que se encuentra en la carpeta templates y agregamos el siguiente código:
1 2 3 4 5 6 7 8 9 |
{% if messages %} <ul class="messages list-group mb-3"> {% for message in messages %} <li{% if message.tags %} class="{{ message.tags }} list-group-item list-group-item-primary"{% endif %}>{{ message }}</li> {% endfor %} </ul> {% endif %} |
Entonces cuando el usuario realice alguna tarea en el sistema CRUD, como editar un registro o jugo, se le va mostrar un mensaje diciendo que la operación ha sido realizada correctamente.
Este mensaje también le va aparecer cuando Crea o Elimina un registro:
Necesitamos una carpeta para subir las imágenes de cada registro, veamos esto a continuación.
Carpeta Para Subir las Imágenes
Debemos crear una carpeta para las imágenes de cada registro que el usuario crea, yo le pondré de nombre uploads a esta carpeta y la creamos dentro de la carpeta crud-django5 > cruddjango5 > jugos > static > uploads:
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 |
/crud-django5 ├── /cruddjango5 ├── /cruddjango5 ├── /jugos ├── /migrations ├── /static ├── /uploads # Creo esta carpeta ├── jf.jpg ├── jn.jpg ├── /templates ├── /jugos ├── actualizar.html // Creamos este archivo ├── crear.html // Creamos este archivo ├── detalles.html // Creamos este archivo ├── index.html // Creamos este archivo ├── __init__.py ├── admin.py ├── apps.py ├── models.py // Abro este archivo ├── test.py ├── views.py ├── db-sqlite3 ├── manage.py ├── /mientornovirtual |
Ahora vamos a realizar algunas configuraciones adicionales.
Configuraciones Adicionales
Recuerda revisar el archivo settings.py alojado en el repositorio GitHub de este proyecto en donde esta toda la configuración que he realizado en todo este tutorial de 5 partes.
Debo destacar las siguientes configuraciones (He colocado comentarios para explicar que hace cada parte del código):
1 2 3 4 5 6 7 8 9 10 11 |
# La URL para los archivos Estáticos (CSS, JS, Imágenes, etc.) STATIC_URL = '/static/' # Las rutas para las imágenes de cada registro o jugo MEDIA_URL = '/jugos/' MEDIA_ROOT = os.path.join(BASE_DIR, 'jugos/static/uploads') # Activamos 'CookieStorage' que nos permite enviar los mensajes de respuesta al Crear, Eliminar y Actualizar un registro MESSAGE_STORAGE = 'django.contrib.messages.storage.cookie.CookieStorage' |
¡ Hemos terminado nuestro sistema CRUD !
Recuerda que ee colocado una Demo al inicio de cada parte del tutorial, para que veas el sistema CRUD en acción, asimismo he colocado el código fuente en GitHub en la última parte del tutorial.
Nota (s)
- Los pasos y opciones mencionadas en esta parte del tutorial pueden cambiar, esto no depende de nosotros, si no de los Desarrolladores que dan soporte a Django y Bootstrap, que suelen cambiar sus opciones de despliegue y configuración en futuras versiones.
- No olvides que debemos usar la Tecnología para hacer cosas Buenas por el Mundo.
Síguenos en nuestras Redes Sociales para que no te pierdas nuestros próximos contenidos.