include() e require()

30 Ott

Out Of Date Warning

Questo post è stato pubblicato più di 2 anni fa (il 30 ottobre 2011). Le idee vanno avanti velocemente, le prospettive cambiano quindi i contenuti potrebbero non essere aggiornati. Ti prego di tenere in considerazione questo, e di verificare le informazioni tecniche presenti nell'articolo prima di farne affidamento per i tuoi scopi.

In PHP le funzioni include() e require() svolgono un ruolo molto importante. Difatti ci permettono di includere files esterni all’interno delle nostre pagine, con l’enorme vantaggio di poter quindi scrivere (ed eventualmente modificare) un’unica volta un blocco di codice che poi verrà incluso all’interno delle pagine.

Le inclusioni Server Side quindi ci fanno risparmiare un sacco di lavoro. Possiamo creare per esempio, un header, un footer o un file di menu per tutte le nostre pagine web. Quando l’header deve essere aggiornato, è possibile solo aggiornare il file di inclusione, oppure quando si aggiunge una nuova pagina al sito, è sufficiente modificare il file menu (invece di aggiornare i links su tutte le pagine).

include() e require() sono esattamente la stessa cosa quando funzionano correttamente, ma si comportano diversamente quando falliscono. Se una funzione include() non funziona (non è possibile includere il file per qualche motivo), un avviso (errore di tipo warning) verrà stampato al browser Web, ma lo script continua a funzionare. Se require() fallisce, verrà stampato un errore (sarà generato un fatal error), e lo script si interomperà.

Percorsi

Possiamo usare qualsiasi tipo di percorso, sia assoluto che relativo per includere il file es:

Un percorso relativo rimarrà “preciso”, anche se spostato su un altro server, a patto che i files mantengano la loro attuale relazione.

Absolute vs. Relative Paths

Prima di proseguire con le nostre due funzioni vorrei fare un po’ di chiarezza sul concetto di percorso assoluto e percorso relativo.
Un percorso assoluto viene creato ogni volta che il collegamento utilizza l’URL completo di un oggetto o di una pagina. Per esempio, http://www.miosito.com è un percorso assoluto di un sito web specifico. Questo metodo è la scelta migliore ogni volta sia necessario inviare un visitatore in un altro sito o si ha la necessità di ottenere il contenuto da un altro sito. Naturalmente lo si può utilizzare anche per pagine interne, ma raramente vi è mai una necessità di farlo.
I percorsi relativi es: "../cartella/pagina.html" sono il tipo più diffuso di collegamento, e per diversi buoni motivi. Difatti ci si può facilmente spostare su e giù per la gerarchia del sito, dentro le varie directories senza problemi e soprattutto se per esempio si vuole spostare il sito da locale sul server questo, funzionerà così cm’è senza dover fare alcun replace dei percorsi.
Attenzione in caso di include (all’interno dei files di inclusione per intenderci) dobbiamo utilizzare un “percorso relativo root” altrimenti i collegamenti non funzioneranno visto che il file di solito si troverà in un posto diverso rispetto ai files che lo includono. Quindi nel creare il percorso si partirà dalla root del sito es: <img src="/images/title.gif">.
Ricapitolando direi che va usato il percorso assoluto per siti esterni mentre percorsi relativi per collegamenti all’interno del nostro sito. Io di solito all’interno delle mie applicazioni tendo ad utilizzare sempre percorsi relativi root che non daranno mai nessun problema.

Le versioni *_once()

All’interno di applicazioni complesse ci si trova spesso nell’impossibilità di stabilire se una pagina è già stata inclusa, con la possibilità quindi di includere più volte lo stesso file.
Questo può portare a problemi anche critici, potrebbe generare per esempio la redifinizione di classi, funzioni, variabili etc.. oppure la riassegnazione di valori alle nostre variabili.
In questo caso PHP ci viene incontro con due apposite versioni della nostre funzioni: include_once() e require_once() che in pratica verificano se un file è già stato inserito ed evitano che si reinserisca un’altra volta.
Queste funzioni effettuano quindi una sorta di controllo di ridondanza, bello in applicazioni complesse, ma possono essere inutili nei siti semplici.

Prestazioni

Naturalmente ci sarà una differenza a livello di prestazioni nell’esecuzione delle nostre quattro funzioni (include(), require(), include_once() e require_once()). Le versioni *_once comportano un overhead di lavoro per il nostro server, in quanto devono passare attraverso l’intera tabella dei files caricati per assicurarsi che il file non sia già stato incluso, prima di aggiungerlo.
Almeno a livello teorico questo è l’ordine dalla più veloce alla più lenta:

  1. include()
  2. require()
  3. include_once()
  4. require_once()

Tuttavia non giurerei su questo ordinamento, questo test PHP require vs. include vs. require_once vs. include_once Performance Test (da prendere con le molle) porta a dei risultati piuttosto sorprendenti! 😯

Tips

  • Posso anche includere una pagina con estensione html contenente codice PHP, funzionerà ugualmente.
  • Se dichiaro una variabile prima dell’include la posso utilizzare anche nel file incluso (anche se .html). Difatti la linea include() ha l’effetto di “far cadere” il contenuto della pagina inclusa all’interno della pagina in quel posto.
  • Tutte le finzioni di inclusione possono contenere URL, ossia files che si trovano su server esterni al sito.
  • Poichè require() ha un impatto maggiore su uno script quando fallisce, è consigliato per inclusioni mission-critical (come quelle che si connettono a un database). La funzione include() sarebbe da usare per inclusioni meno importanti. Le versioni *_once() sono per il controllo di ridondanza, utili in applicazioni complesse, ma possono essere inutili nei siti semplici.
  • È raccomandato usare estensioni .inc o .html per documenti in cui la sicurezza non è un problema (come modelli HTML) e .php per i files che contengono dati più sensibili (come le informazioni di accesso al database).

Risorse

include()
require()
include_once()
require_once()
PHP require vs. include vs. require_once vs. include_once Performance Test

Lascia un commento