Python Django: vediamo i templates
Siamo finalmente giunti al momento di mettere mano ai template HTML e di conseguenza vedere qualcosa dal lato grafico.
Nel capitolo 04 abbiamo visto che nel definire le liste dei post o del dettaglio, la funzione terminava indicando un file HTML in una path precisa, ovvero blog/post/post.html
Essendo questo un template andremo a creare una cartella “templates” all’interno della cartella “blog” che avrà questa struttura:
templates/
blog/
container.html
post/
list.html
post.html
NOTA: sotto templates il nome della cartella deve essere obbligatoriamente quello della nostra App
Consiglio di creare nel vostro editor, ad esempio Visual Studio Code, i file vuoti in modo da avere la struttura già pronta. Partiamo con il file “container.html” che deve appunto contenere tutte le parti che di solito non cambiano, ad esempio “header e footer”.
container.html
{% load static %}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{% block title %}{% endblock title %}</title>
</head>
<body>
<div id="container">
{% block content %}
{% endblock content %}
</div>
</body>
</html>
Come possiamo subito vedere dalla prima linea, il file HTML contiene della codifica aliena derivata da Django. Possiamo infatti inserire degli elementi che sono tag, variabili o variabili con filtro:
{% tag %}
{{ variabile_django }}
{{ variabile_django|filtro }}
La referenza dei “tag” la troviamo a questa pagina della documentazione di Django.
È probabile che avrete già cominciato ad intuire le potenzialità del sistema, si può costruire una base di template in HTML5 e poi espanderla con i dati dinamici di Django. Come però è ben noto una pagina senza fogli di stile non va da nessuna parte; quindi, aggiungiamo BootStrap5 ed un file di appoggio per personalizzazioni.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{% block title %}{% endblock title %}</title>
<link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-T3c6CoIi6uLrA9TneNEoa7RxnatzjcDSCmG1MXxSR1GAsXEV/Dwwykc2MPK8M2HN" crossorigin="anonymous">
<link href="{% static "css/style.css" %}" rel="stylesheet">
</head>
<body class="p-3 m-0 border-0 bd-example m-0 border-0">
<div id="container">
{% block content %}
{% endblock content %}
</div>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/js/bootstrap.bundle.min.js" integrity="sha384-C6RzsynM9kWDrMNeT87bh95OGNyZPhcTNXj1NW7RuBCsyN/o0jlpcV8Qyq46cDfL" crossorigin="anonymous"></script>
</body>
</html>
Se nel caso di Bootstrap si fa riferimento a librerie che stanno su Internet, nella personalizzazione siamo andati ad indicare un file “{% static “css/style.css” %}”.
All’interno della cartella “blog” andremo a creare una sottocartella “static” e al suo interno una ulteriore “css”, dove possiamo creare il file style.css. Per il momento abbiamo concluso con container, ma ci ritorneremo per aggiungere ad esempio una sidebar.
Passiamo al file list.html che deve contenere la lista dei post.
list.html
{% extends 'container.html' %}
{% block title %}
Blog posts
{% endblock title %}
{% block content %}
<h1>Blog Posts</h1>
{% for post in posts %}
<div class="row row-cols-1 p-2">
<div class="col">
<div class="card">
<div class="card-header">
<a href="{{ post.get_absolute_uri }}">{{ post.title }}</a>
</div>
<div class="card-body">
{{ post.body|truncatewords:50|linebreaks}}
</div>
<div class="card-footer text-body-secondary">
Published {{ post.publish}} by {{ post.author}}
</div>
</div>
</div>
</div>
{% endfor %}
{% endblock content %}
Faccio subito notare la riga 1, che va a prendere il file precedente, ovvero container.html e lo “estende” prima del resto del codice. Il titolo viene poi passato a “container” mentre il content espande appunto la funzione, in questo caso della lista dei post, sul file che abbiamo visto in precedenza.
Body (linea 17) invece è “tagliato” quando le parole sono sopra le 50, aggiungendo un linebreak finale.
Un primo risultato dovrebbe risultarvi come l’immagine che segue.
Post singolo
Andiamo a completare la nostra bozza, andando ad aggiungere, in modo molto simile a quanto già fatto, ma per il post singolo. Il file da modificare è “post.html”
post.html
{% extends 'container.html' %}
{% block title %} {{ post.title }} {% endblock title %}
{% block content %}
<div class="row row-cols-1 p-2">
<div class="col">
<div class="card">
<div class="card-header">
{{ post.title }}
</div>
<div class="card-body">
{{ post.body|linebreaks }}
</div>
<div class="card-footer">
Published {{ post.publish }} by {{ post.author }}
</div>
</div>
</div>
</div>
{% endblock content %}
A questo punto abbiamo un sistema front-end sostanzialmente funzionante, anche se un po’ rozzo. Ad esempio, manca una navigation bar che nel caso del post aiuterebbe a tornare indietro. E tanti altri piccoli dettagli che vedremo nei prossimi capitoli.
Posted from my blog: https://blog.tosolini.info/