Flask genera un errore TemplateNotFound anche se il file modello esiste


107

Sto cercando di eseguire il rendering del file home.html. Il file esiste nel mio progetto, ma continuo a visualizzarlo jinja2.exceptions.TemplateNotFound: home.htmlquando provo a renderlo. Perché Flask non riesce a trovare il mio modello?

from flask import Flask, render_template

app = Flask(__name__)

@app.route('/')
def home():
    return render_template('home.html')
/myproject
    app.py
    home.html

Risposte:


212

È necessario creare i file del modello nella posizione corretta; nella templatessottodirectory accanto al tuo modulo python.

L'errore indica che non è presente alcun home.htmlfile nella templates/directory. Assicurati di aver creato quella directory nella stessa directory del tuo modulo python e di aver effettivamente messo un home.htmlfile in quella sottodirectory. Se la tua app è un pacchetto, la cartella dei modelli dovrebbe essere creata all'interno del pacchetto.

myproject/
    app.py
    templates/
        home.html
myproject/
    mypackage/
        __init__.py
        templates/
            home.html

In alternativa, se hai chiamato la cartella dei modelli in modo diverso da templatese non vuoi rinominarla come predefinita, puoi dire a Flask di usare l'altra directory.

app = Flask(__name__, template_folder='template')  # still relative to module

Puoi chiedere a Flask di spiegare come ha cercato di trovare un determinato modello, impostando l' EXPLAIN_TEMPLATE_LOADINGopzione su True. Per ogni modello caricato, riceverai un rapporto registrato nel Flaskapp.logger , a livello INFO.

Ecco come appare quando una ricerca ha esito positivo; in questo esempio il foo/bar.htmltemplate estende il base.htmltemplate, quindi ci sono due ricerche:

[2019-06-15 16:03:39,197] INFO in debughelpers: Locating template "foo/bar.html":
    1: trying loader of application "flaskpackagename"
       class: jinja2.loaders.FileSystemLoader
       encoding: 'utf-8'
       followlinks: False
       searchpath:
         - /.../project/flaskpackagename/templates
       -> found ('/.../project/flaskpackagename/templates/foo/bar.html')
[2019-06-15 16:03:39,203] INFO in debughelpers: Locating template "base.html":
    1: trying loader of application "flaskpackagename"
       class: jinja2.loaders.FileSystemLoader
       encoding: 'utf-8'
       followlinks: False
       searchpath:
         - /.../project/flaskpackagename/templates
       -> found ('/.../project/flaskpackagename/templates/base.html')

I blueprint possono anche registrare le proprie directory di modelli , ma questo non è un requisito se si utilizzano blueprint per rendere più semplice la suddivisione di un progetto più grande in unità logiche. La directory principale dei modelli di app Flask viene sempre cercata per prima anche quando si utilizzano percorsi aggiuntivi per progetto.


2
EXPLAIN_TEMPLATE_LOADING è molto utile per eseguire il debug dei problemi di percorso attorno ai modelli. Inoltre, se utilizzi Blueprints, assicurati di impostare il template_folderpercorso per blueprint .
Justin Krause,

1
@JustinKrause: grazie per quelli, è EXPLAIN_TEMPLATE_LOADINGstato aggiunto dopo che questa risposta è stata inizialmente scritta.
Martijn Pieters

1
Sembra che il mio flask locale (su Windows) possa trovare modelli all'interno ./Templates/index.html, ma quando eseguo il deployment su heroku (pensavo fosse lo stesso Python, stesse versioni della libreria, inclusa la stessa versione di Flask; ma heroku è Unix); e lancia TemplateNotFounderrore; dopo aver rinominato la cartella git mv Templates/index.html templates/index.html, entrambe le versioni locale (Windows) e heroku (Unix) hanno funzionato
The Red Pea

1
@TheRedPea sì, perché il file system di Windows ripiega il caso Templates== templates. Ma Heroku esegue Linux, con un filesystem case sensitive.
Martijn Pieters

11

Penso che Flask utilizzi i modelli di directory per impostazione predefinita. Quindi il tuo codice dovrebbe essere supponiamo che questo sia il tuo hello.py

from flask import Flask,render_template

app=Flask(__name__,template_folder='template')


@app.route("/")
def home():
    return render_template('home.html')

@app.route("/about/")
def about():
    return render_template('about.html')

if __name__=="__main__":
    app.run(debug=True)

E lavori come la struttura dello spazio

project/
    hello.py        
    template/
         home.html
         about.html    
    static/
           js/
             main.js
           css/
               main.css

inoltre hai creato due file html con il nome di home.html e about.html e metti quei file nella cartella dei modelli.


8

(Si prega di notare che la risposta sopra accettata fornita per la struttura del file / progetto è assolutamente corretta.)

Anche..

Oltre a impostare correttamente la struttura del file di progetto, dobbiamo dire a flask di cercare nel livello appropriato della gerarchia di directory.

per esempio..

    app = Flask(__name__, template_folder='../templates')
    app = Flask(__name__, template_folder='../templates', static_folder='../static')

Iniziando con si ../sposta una directory indietro e inizia da lì.

Iniziare con ../../sposta due directory indietro e inizia da lì (e così via ...).

Spero che questo ti aiuti


4

Non so perché, ma ho dovuto utilizzare la seguente struttura di cartelle. Ho messo "modelli" di un livello in alto.

project/
    app/
        hello.py
        static/
            main.css
    templates/
        home.html
    venv/

Questo probabilmente indica un errore di configurazione altrove, ma non sono riuscito a capire cosa fosse e ha funzionato.


3

Controllalo:

  1. il file modello ha il nome corretto
  2. il file modello si trova in una sottodirectory chiamata templates
  3. il nome a cui passi render_templateè relativo alla directory dei modelli ( index.htmlsarebbe direttamente nella directory dei modelli, auth/login.htmlsarebbe sotto la directory auth nella directory dei modelli).
  4. o non hai una sottodirectory con lo stesso nome della tua app, oppure la directory dei modelli si trova all'interno di quella sottodirectory.

Se non funziona, attiva debugging ( app.debug = True) che potrebbe aiutare a capire cosa c'è che non va.


3

Se esegui il codice da un pacchetto installato, assicurati che i file modello siano presenti nella directory <python root>/lib/site-packages/your-package/templates.


Alcuni dettagli:

Nel mio caso stavo cercando di eseguire esempi del progetto flask_simple_ui e dicevojinja sempre

jinja2.exceptions.TemplateNotFound: form.html

Il trucco era che il programma di esempio importava il pacchetto installato flask_simple_ui. E ninjaessere usato dall'interno di quel pacchetto sta usando come directory principale per cercare il percorso del pacchetto, nel mio caso ...python/lib/site-packages/flask_simple_ui, invece di os.getcwd() come ci si aspetterebbe.

Per mia sfortuna, setup.pyha un bug e non copia alcun file html, compresi quelli mancanti form.html. Una volta risolto setup.py, il problema con TemplateNotFound è svanito.

Spero che aiuti qualcuno.


2

Ho avuto lo stesso errore e l'unica cosa che ho fatto di sbagliato è stata nominare la mia cartella "modelli", "modello" senza "s". Dopo aver cambiato che ha funzionato bene, non so perché è una cosa ma lo è.


2

Quando viene utilizzata la funzione render_template (), tenta di cercare il modello nella cartella chiamata modelli e genera l'errore jinja2.exceptions.TemplateNotFound quando:

  1. il file html non esiste o
  2. quando la cartella dei modelli non esiste

Per risolvere il problema :

creare una cartella con i modelli di nome nella stessa directory in cui si trova il file python e posizionare il file html creato nella cartella dei modelli.


1

Devi mettere tutti i tuoi .htmlfile nella cartella dei modelli accanto al tuo modulo python. E se ci sono immagini che stai usando nei tuoi file html, allora devi mettere tutti i tuoi file nella cartella denominata static

Nella seguente struttura

project/
    hello.py
    static/
        image.jpg
        style.css
    templates/
        homepage.html
    virtual/
        filename.json

1

Un'altra alternativa è impostare il root_pathche risolve il problema sia per i modelli che per le cartelle statiche.

root_path = Path(sys.executable).parent if getattr(sys, 'frozen', False) else Path(__file__).parent
app = Flask(__name__.split('.')[0], root_path=root_path)

Se esegui il rendering dei modelli direttamente tramite Jinja2, scrivi:

ENV = jinja2.Environment(loader=jinja2.FileSystemLoader(str(root_path / 'templates')))
template = ENV.get_template(your_template_name)
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.