Domanda modelli di Django: include ed estende


Vorrei fornire lo stesso contenuto in 2 diversi file di base.

Quindi sto cercando di farlo:

page1.html:

{% extends "base1.html" %}
{% include "commondata.html" %}

page2.html:

{% extends "base2.html" %} 
{% include "commondata.html" %}

Il problema è che non riesco a usare entrambe le estensioni e include. C'è un modo per farlo? E se no, come posso realizzare quanto sopra?

commondata.html sovrascrive un blocco specificato in base1.html e base2.html

Lo scopo di questo è di fornire la stessa pagina sia in formato pdf che html, in cui la formattazione è leggermente diversa. La domanda sopra però semplifica ciò che sto cercando di fare in modo che se riesco a ottenere una risposta, risolverà il mio problema.


82
2017-09-11 04:08


origine


risposte:


Quando si utilizza l'estensione del tag del modello, si sta dicendo che il modello corrente ne estende un altro - che si tratta di un modello figlio, dipendente da un modello principale. Django guarderà il tuo modello figlio e userà il suo contenuto per popolare il genitore.

Tutto ciò che si desidera utilizzare in un modello figlio deve trovarsi all'interno di blocchi, che Django utilizza per popolare il genitore. Se vuoi usare un'istruzione include in quel template secondario, devi metterlo all'interno di un blocco, perché Django possa dare un senso a questo. Altrimenti non ha senso e Django non sa cosa farsene.

La documentazione di Django contiene alcuni esempi di utilizzo dei blocchi per sostituire i blocchi nel modello principale.

https://docs.djangoproject.com/en/dev/ref/templates/language/#template-inheritance


88
2017-09-11 04:13



Da documenti Django:

Il tag include deve essere considerato come un'implementazione di "render this subtemplate e include l'HTML", non come "analizzare questo sotto-titolo e includerne il contenuto come se fosse parte del genitore". Ciò significa che non esiste uno stato condiviso tra i modelli inclusi: ogni inclusione è un processo di rendering completamente indipendente.

Quindi Django non prende nessun blocco dal tuo commondata.html e non sa cosa fare con i blocchi html resi all'esterno.


68
2017-11-08 21:55



Maggiori informazioni sul motivo per cui non ha funzionato per me nel caso in cui aiuti le persone future:

Il motivo per cui non funzionava è che {% include%} in django non ama i caratteri speciali come l'apostrofo di fantasia. I dati del modello che stavo cercando di includere sono stati incollati dalla parola. Ho dovuto rimuovere manualmente tutti questi caratteri speciali e quindi incluso correttamente.


10
2017-09-11 05:21



Questo dovrebbe fare il trucco per te: metti tag include all'interno di una sezione di blocco.

page1.html:

{% extends "base1.html" %}

{% block foo %}
   {% include "commondata.html" %}
{% endblock %}

page2.html:

{% extends "base2.html" %}

{% block bar %}
   {% include "commondata.html" %}
{% endblock %}

7
2018-05-10 14:29



Non è possibile inserire blocchi da un file incluso in un modello secondario per sovrascrivere i blocchi del modello principale. Tuttavia, è possibile specificare un genitore in una variabile e avere il modello di base specificato nel contesto.

Dal documentazione:

{% estende la variabile%} utilizza il valore della variabile. Se la variabile valuta una stringa, Django utilizzerà tale stringa come nome del modello principale. Se la variabile valuta un oggetto Template, Django utilizzerà tale oggetto come modello principale.

Invece di "page1.html" e "page2.html" separati, inserisci {% extends base_template %}nella parte superiore di "commondata.html". E poi, a tuo avviso, definisci base_template essere "base1.html" o "base2.html".


3
2018-04-19 18:57



Aggiunto per riferimento alle persone future che trovano questo tramite google: potresti voler esaminare il tag {% overextend%} fornito dalla libreria mezzanine per casi come questo.


2
2017-12-15 21:34



Modifica 10 dicembre 2015: Come sottolineato nei commenti, ssi è deprecato dalla versione 1.8. Secondo la documentazione:

Questo tag è stato deprecato e verrà rimosso in Django 1.10. Utilizza invece il tag include.


A mio parere, la risposta giusta (la migliore) a questa domanda è quella di podshumok, in quanto spiega perché il comportamento di include se usato insieme all'ereditarietà.

Tuttavia, sono stato un po 'sorpreso dal fatto che nessuno abbia menzionato il ssi tag fornito dal sistema di template di Django, appositamente progettato per in linea compreso un pezzo esterno di testo. Qui, in linea significa che il testo esterno non sarà interpretato, analizzato o interpolato, ma semplicemente "copiato" all'interno del modello chiamante.

Per favore, fai riferimento alla documentazione per ulteriori dettagli (assicurati di controllare la versione appropriata di Django nel selettore nella parte in basso a destra della pagina).

https://docs.djangoproject.com/en/dev/ref/templates/builtins/#ssi

Dalla documentazione:

ssi
Outputs the contents of a given file into the page.
Like a simple include tag, {% ssi %} includes the contents of another file
– which must be specified using an absolute path – in the current page

Fate attenzione anche alle implicazioni di sicurezza di questa tecnica e anche alla definizione necessaria di ALLOWED_INCLUDE_ROOTS, che deve essere aggiunta ai file delle impostazioni.


1
2018-05-13 08:24