Jinja2-Templates — HTML-Seiten rendern

In diesem Kapitel lernen Sie, die Jinja2-Template-Engine zu verwenden, um vollständige HTML-Seiten zu rendern und gemeinsame Layouts zu extrahieren.


Von Strings zu Templates

Im vorherigen Kapitel gaben View-Funktionen direkt Strings mit in den Zeilen eingebetteten HTML-Tags zurück, die nicht wiederverwendet werden konnten und schwer zu warten waren.

render_template()Es ist der Einstiegspunkt für das Template-Rendering von Flask: Es lädt HTML-Dateien, fügt Variablen ein und gibt eine vollständige HTML-Antwort zurück.

Beispiel

# Dateipfad: app.py
from flask import Flask, render_template

app = Flask(__name__)

@app.route("/")
def index():
    # render_template('Template-Dateiname', Variablenname=Wert, ...)
    return render_template('index.html', title='EXAMPLE Blog')

Flask standardmäßig im Stammverzeichnis des Projektstemplates/Templates im Ordner finden.


Template-Dateien erstellen

Im Projektstammverzeichnis erstellentemplates/Ordner, dann erstellenindex.html。

Beispiel

<!-- Dateipfad: templates/index.html -->
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <title>{{ title }}</title>
</head>
<body>
    <h1>{{ title }}</h1>
    <p>Willkommen, dies ist eine Seite, die mit der Jinja2-Template-Engine gerendert wurde.</p>
</body>
</html>

Überblick über die Jinja2-Template-Syntax

Die Jinja2-Syntax ist fast genau dieselbe wie die Django-Template-Syntax und ähnelt auch der Interpolationssyntax von Vue.

ZweckJinja2 / DjangoBeschreibung
Ausgabevariablen{{ variable }}Unterstützt Attributzugriff: {{ user.name }}
Schleifen{% for item in list %}...{% endfor %}Unterstützt loop.index
Bedingungen{% if cond %}...{% endif %}Verkettbar: {% elif %}
Vererbung{% extends 'base.html' %}Muss in der ersten Zeile stehen
Blockdefinitionen{% block name %}...{% endblock %}Kind-Templates füllen die Lücken des Eltern-Templates

Die Template-Syntax von Jinja2 und Django ist nahezu identisch, aber Jinja2 ist flexibler: Du kannst komplexere Python-Ausdrücke in Templates schreiben, während Django-Templates einige Fähigkeiten bewusst einschränken, um zu vermeiden, dass Geschäftslogik in Templates durchsickert.


Template-Vererbung: base.html

Mehrere Seiten teilen die Navigationsleiste und den Footer, verwendeTemplate-Vererbung, um doppeltes HTML zu vermeiden.

Erstellen eines base.html-Eltern-Templates

Beispiel

<!-- Dateipfad: templates/base.html -->
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <!-- block title: Kind-Template kann den Seitentitel überschreiben -->
    <title>{% block title %}EXAMPLE Blog{% endblock %}</title>
    <style>
        * { margin: 0; padding: 0; box-sizing: border-box; }
        body {
            font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
            background: #f5f5f5;
            color: #333;
        }
        .navbar {
            display: flex; justify-content: space-between; align-items: center;
            padding: 16px 40px; background: #fff;
            box-shadow: 0 2px 8px rgba(0,0,0,0.1);
        }
        .navbar .logo { font-size: 22px; font-weight: bold; color: #e74c3c; text-decoration: none; }
        .navbar a { margin-left: 20px; text-decoration: none; color: #333; }
        .container { max-width: 960px; margin: 40px auto; padding: 0 20px; }
        .footer { text-align: center; padding: 20px; color: #999; border-top: 1px solid #eee; }
    </style>
    {% block extra_head %}{% endblock %}
</head>
<body>
    <header class="navbar">
        <a href="/" class="logo">BEISPIEL Blog (Flask)</a>
        <nav>
            <a href="/">Startseite</a>
            <a href="/about">Über uns</a>
        </nav>
    </header>

    <main class="container">
        <!-- Blockinhalt: Kind-Template füllt hier den Hauptinhalt der Seite ein -->
        {% block content %}
        {% endblock %}
    </main>

    <footer class="footer">
        <p>© 2024 EXAMPLE Blog. Bereitgestellt von Flask.</p>
    </footer>
</body>
</html>

Kind-Templates erben vom übergeordneten Template

Beispiel

<!-- Dateipfad: templates/index.html -->
{% extends 'base.html' %}

{% block title %}EXAMPLE Blog - Startseite{% endblock %}

{% block content %}
<h2>Neueste Artikel</h2>
<p>Die Artikelliste wird in späteren Kapiteln angezeigt.</p>
{% endblock %}

{% extends 'base.html' %}Es muss in der ersten Zeile des Kind-Templates stehen (außer bei Kommentaren). Dies ist eine harte Anforderung von Jinja2 – die Template-Engine muss zuerst die Vererbungsbeziehung bestimmen.


url_for() erzeugt Links

URLs nicht fest kodieren, verwendeurl_for(), um die Adresse anhand des Funktionsnamens nachzuschlagen.

Beispiel

# Routen-Endpunkt in views.py definieren
@app.route("/")
def index(): ...

@app.route("/post/<int:post_id>")
def post_detail(post_id): ...

Beispiel

[mycode4 type="html"> In Templates erzeugt url_for() Links Startseite Artikel 3 Verweisen auf statische Dateien [/mycode4]

Die Route hat sich geändert (z. B.,/post/Wechsel zu/article/), im Templateurl_for()Automatisch neue Adressen generieren.


Konfiguration statischer Dateien

Flask wird standardmäßigstatic/Verzeichnis als Stammverzeichnis für statische Dateien.

blog_project/
├── static/
│   ├── css/
│   │   └── style.css
│   ├── js/
│   │   └── main.js
│   └── images/
│       └── logo.png
├── templates/
└── app.py

In Templates, überurl_for('static', filename='css/style.css')referenzieren.


Kapitelzusammenfassung

In diesem Kapitel hast du den Kern der Jinja2-Templates beherrscht: render_template() zum Rendern von Templates, {{ }} zur Ausgabe von Variablen, {% for/if %} Kontrollfluss, base.html + block + extends Template-Vererbung und url_for() zum Generieren von Links.

Jetzt ist die Blogseite gut strukturiertes HTML geworden, und die gemeinsamen Teile wurden in base.html ausgelagert.

Weitere Erweiterungen