Quando dovrei usare Inline vs. Javascript esterno?


129

Vorrei sapere quando dovrei includere script esterni o scriverli in linea con il codice HTML, in termini di prestazioni e facilità di manutenzione.

Qual è la pratica generale per questo?

Scenario del mondo reale - Ho diverse pagine html che richiedono la convalida dei moduli sul lato client. Per questo utilizzo un plug-in jQuery che includo in tutte queste pagine. Ma la domanda è: devo:

  • scrivere i bit di codice che configurano questo script in linea?
  • includere tutti i bit in un file condiviso tra tutte queste pagine html?
  • includere ogni bit in un file esterno separato, uno per ogni pagina html?

Grazie.

Risposte:


114

All'epoca in cui questa risposta era stata originariamente pubblicata (2008), la regola era semplice: tutto lo script doveva essere esterno. Sia per manutenzione che per prestazioni.

(Perché prestazioni? Perché se il codice è separato, può essere più facilmente memorizzato nella cache dai browser.)

JavaScript non appartiene al codice HTML e se contiene caratteri speciali (come <, ad esempio >) crea persino problemi.

Oggi la scalabilità del web è cambiata. La riduzione del numero di richieste è diventata una considerazione valida a causa della latenza di effettuare più richieste HTTP. Questo rende la risposta più complessa: nella maggior parte dei casi, dopo aver è JavaScript esterno ancora raccomandato. Ma per alcuni casi, specialmente pezzi di codice molto piccoli, inserirli nell'HTML del sito ha senso.


6
@Nick: la maggior parte dei problemi può essere superata. Meglio non generarli in primo luogo, comunque.
Konrad Rudolph,

17
A volte si ottengono prestazioni migliori durante l'allineamento. Guarda la fonte di google.com . Sanno cosa stanno facendo.
callum,

13
@callum Google ha un caso d'uso diverso dal 99.999999% dei siti Web. Ovviamente misurano con estrema attenzione e anche la minima differenza conta. Ma solo perché hanno scoperto che nel loro particolare caso d'uso, l'inline funziona meglio (probabilmente perché lo script cambia molto frequentemente?) Non significa che possiamo derivarne una regola generale, o anche che dovremmo ignorare il "convenzionale" regola (per esternalizzare gli script).
Konrad Rudolph,

8
@KonradRudolph - D'accordo, nessuna regola generale dovrebbe essere derivata dall'approccio di Google. Sto solo dicendo che può essere utile mettere in discussione la regola nella tua risposta. Ad ogni modo, penso che il motivo per cui Google lo fa sia quello di ridurre le richieste HTTP, e questo potrebbe beneficiare di oltre lo 0,000001% dei siti. La larghezza di banda sta aumentando, ma i tempi di andata e ritorno rimangono gli stessi. La rimozione di un'intera richiesta HTTP seriale è talvolta migliore del vantaggio della memorizzazione nella cache di JS esterno. Dipende ovviamente dalle dimensioni del tuo JS.
callum,

5
@callum Mentre questo è vero, il punto sulla memorizzazione nella cache rimane e rimane importante. Ridurre i viaggi di andata e ritorno è importante solo se i tuoi visitatori non ritornano (e quindi non otterrai abbastanza risultati sulla pagina per renderli importanti) o se il tuo contenuto cambia così spesso che la memorizzazione nella cache dei file di script non ha alcun vantaggio.
Konrad Rudolph,

31

La manutenibilità è sicuramente un motivo per mantenerli esterni, ma se la configurazione è di tipo one-liner (o in generale più corta dell'overhead HTTP che si otterrebbe per rendere quei file esterni) è meglio dal punto di vista delle prestazioni mantenerli in linea. Ricorda sempre che ogni richiesta HTTP genera un sovraccarico in termini di tempo di esecuzione e traffico.

Naturalmente tutto ciò diventa irrilevante nel momento in cui il codice è più lungo di un paio di righe e non è realmente specifico per una singola pagina. Nel momento in cui vuoi poter riutilizzare quel codice, rendilo esterno. In caso contrario, guarda le sue dimensioni e decidi quindi.


5
Questa è una delle mie preoccupazioni. Avere una richiesta HTTP separata per poche righe di codice sembra dispendioso.
Dan Burzo,

Potresti forse pubblicare una configurazione di esempio per il tuo codice? IMO se ha meno di 300 caratteri e assolutamente specifico della pagina, incorporalo.
Horst Gutmann,

Questa dovrebbe essere la risposta migliore imo
sgarcia.dev

@Dan tenere presente che la richiesta separata avviene solo la prima volta. Se ti aspetti che i tuoi utenti caricino la pagina più di una volta, la cache esterna (anche per poche righe) è chiaramente più veloce dell'attesa dei byte per quelle poche righe sul filo sui n = 2 + caricamenti di pagine.
jinglesthula,

@HorstGutmann come può avere il file un aiuto esterno con manutenibilità? Personalmente preferisco js esterni ogni volta che è possibile, ma esiste qualcosa di oggettivo che lo rende più facile da mantenere?
jinglesthula,

21

Esternalizzare javascript è una delle regole di performance di yahoo: http://developer.yahoo.com/performance/rules.html#external

Mentre la regola rigida che dovresti sempre esternalizzare gli script sarà generalmente una buona scommessa, in alcuni casi potresti voler incorporare alcuni degli script e degli stili. Tuttavia, dovresti solo incorporare cose che sai miglioreranno le prestazioni (perché l'hai misurato).


1
Penso che Yahoo consiglia anche di aggiungere tutto il Javascript anche in una chiamata HTTP - questo non significa che gli script dovrebbero essere tutti nello stesso file durante lo sviluppo
Paul Shannon,

Inoltre, come notato sopra, HTTP / 2 cambia anche la pratica "1 chiamata".
jinglesthula,

19

Se ti preoccupi solo delle prestazioni, la maggior parte dei consigli in questo thread è completamente sbagliata e sta diventando sempre più sbagliata nell'era SPA, dove possiamo presumere che la pagina sia inutile senza il codice JS. Ho trascorso innumerevoli ore a ottimizzare i tempi di caricamento della pagina SPA e a verificare questi risultati con diversi browser. Su tutta la linea l'aumento delle prestazioni riorganizzando il tuo HTML, può essere abbastanza drammatico.

Per ottenere le migliori prestazioni, devi pensare alle pagine come a razzi a due stadi. Queste due fasi corrispondono approssimativamente a <head>e <body>fasi, ma pensali invece come <static>e <dynamic>. La parte statica è fondamentalmente una costante di stringa che spinge giù il tubo di risposta il più velocemente possibile. Questo può essere un po 'complicato se usi un sacco di middleware che imposta i cookie (questi devono essere impostati prima di inviare il contenuto http), ma in linea di principio sta semplicemente svuotando il buffer di risposta, si spera prima di saltare in un codice di template (rasoio, php, ecc.) sul server. Può sembrare difficile, ma poi lo sto solo spiegando male, perché è quasi banale. Come avrai intuito, questa parte statica dovrebbe contenere tutti i javascript incorporati e minimizzati. Sembrerebbe qualcosa del genere

<!DOCTYPE html>
     <html>
         <head>
             <script>/*...inlined jquery, angular, your code*/</script>
             <style>/* ditto css */</style>
         </head>
         <body>
             <!-- inline all your templates, if applicable -->
             <script type='template-mime' id='1'></script>
             <script type='template-mime' id='2'></script>
             <script type='template-mime' id='3'></script>

Dal momento che non ti costa quasi nulla inviare questa porzione via cavo, puoi aspettarti che il client inizierà a riceverla da qualche parte circa 5ms + latenza dopo la connessione al tuo server. Supponendo che il server sia ragionevolmente vicino questa latenza potrebbe essere compresa tra 20 e 60 ms. I browser inizieranno a elaborare questa sezione non appena la ottengono e il tempo di elaborazione normalmente dominerà il tempo di trasferimento per il fattore 20 o più, che è ora la finestra ammortizzata per l'elaborazione lato server della <dynamic>porzione.

Ci vogliono circa 50ms per il browser (Chrome, resto forse più lento del 20%) per elaborare jquery in linea + signalr + angular + ng animate + ng touch + ng route + lodash. È piuttosto sorprendente in sé e per sé. La maggior parte delle app Web ha meno codice di tutte quelle popolari librerie messe insieme, ma diciamo che ne hai altrettanto, quindi vinceremo latenza + 100 ms di elaborazione sul client (questa vincita di latenza viene dal secondo blocco di trasferimento). Quando arriva il secondo pezzo, abbiamo elaborato tutto il codice js e i modelli e possiamo iniziare a eseguire le trasformazioni dom.

Potresti obiettare che questo metodo è ortogonale al concetto in linea, ma non lo è. Se invece di inline, ti colleghi a cdns o ai tuoi server, il browser dovrebbe aprire un'altra connessione e ritardare l'esecuzione. Poiché questa esecuzione è sostanzialmente gratuita (poiché il lato server sta parlando con il database), deve essere chiaro che tutti questi salti costerebbero di più rispetto a non fare affatto salti. Se ci fosse una stranezza del browser che dicesse che js esterno viene eseguito più velocemente, potremmo misurare quale fattore domina. Le mie misurazioni indicano che in questo momento le richieste extra uccidono le prestazioni.

Lavoro molto con l'ottimizzazione delle app SPA. È comune per le persone pensare che il volume dei dati sia un grosso problema, mentre in verità la latenza e l'esecuzione spesso dominano. Le librerie minimizzate che ho elencato aggiungono fino a 300kb di dati, e questo è solo 68 kb gzipped, o 200ms download su un telefono 2m 3g / 4g, che è esattamente la latenza che sarebbe lo stesso telefono per verificare se avesse gli stessi dati nella sua cache già, anche se era in proxy proxy, perché si applica ancora la tassa di latenza mobile (latenza da telefono a tower). Nel frattempo, le connessioni desktop che hanno una latenza di primo passaggio inferiore in genere hanno comunque una larghezza di banda maggiore.

In breve, proprio ora (2014), è meglio incorporare tutti gli script, gli stili e i modelli.

EDIT (MAGGIO 2016)

Man mano che le applicazioni JS continuano a crescere e alcuni dei miei payload ora accumulano fino a 3+ megabyte di codice minimizzato, sta diventando ovvio che almeno le librerie più comuni non dovrebbero più essere incorporate.


Non ho ricevuto quella che ora è la tua finestra ammortizzata per l'elaborazione lato server della parte della porzione <dinamica> - Il server elabora tutto ciò di cui ha bisogno e solo allora serve l'intero html renderizzato (head + body), quale altra elaborazione server è necessario dopo?
BornToCode

@BornToCode L'idea è quella di dare al cliente qualcosa da fare allo stesso tempo, il lato server ha qualcosa da fare. Poiché le librerie client devono essere interpretate, è meglio avviare quel processo prima di eseguire qualsiasi calcolo sul server. La finestra ammortizzata è il tempo impiegato dal client per elaborare JS. Ottieni quella finestra gratuitamente se orchetti un razzo a 2 stadi.
Gleno,


9

In realtà, c'è un caso abbastanza solido per usare javascript in linea. Se js è abbastanza piccolo (one-liner), tendo a preferire il javascript in linea a causa di due fattori:

  • Località . Non è necessario navigare in un file esterno per convalidare il comportamento di alcuni javascript
  • AJAX . Se stai rinfrescante qualche sezione della pagina tramite la tecnologia AJAX, si può perdere tutti i gestori di DOM (onclick, ecc) per quella sezione, a seconda di come li rilegata. Ad esempio, usando jQuerytu puoi usare i metodi liveo delegateper aggirare questo, ma trovo che se js è abbastanza piccolo è preferibile metterlo in linea.

5

Un altro motivo per cui dovresti sempre usare script esterni è per una più facile transizione alla politica di sicurezza dei contenuti (CSP) . I valori predefiniti CSP vietano tutti gli script inline, rendendo il tuo sito più resistente agli attacchi XSS.


4

Darei un'occhiata al codice richiesto e lo dividerei in tutti i file separati necessari. Ogni file js conterrebbe solo un "insieme logico" di funzioni ecc. Ad es. un file per tutte le funzioni relative all'accesso.

Quindi durante lo sviluppo del sito su ogni pagina html includi solo quelli necessari. Quando vai online con il tuo sito puoi ottimizzare ottimizzando tutti i file js di cui una pagina ha bisogno in un unico file.


4

L'unica difesa che posso offrire per javascipt inline è che quando si usano viste fortemente tipizzate con .net MVC è possibile fare riferimento a variabili c # mid javascript che ho trovato utili.


3

Tre considerazioni:

  • Di quanto codice hai bisogno (a volte le librerie sono un consumatore di prima classe)?
  • Specificità: questo codice funziona solo nel contesto di questo documento o elemento specifico?
  • Ogni codice all'interno del documento tende a renderlo più lungo e quindi più lento. Oltre a ciò le considerazioni SEO rendono ovvio che minimizzi gli script interni ...

2

Gli script esterni sono anche più facili da eseguire il debug utilizzando Firebug. Mi piace provare Unit JavaScript e avere tutti gli aiuti esterni. Odio vedere JavaScript nel codice PHP e HTML mi sembra un gran casino.


2

Sul punto di mantenere JavaScript esterno:

ASP.NET 3.5SP1 ha recentemente introdotto la funzionalità per creare una risorsa di script composito (unire un gruppo di file js in uno). Un altro vantaggio di questo è quando la compressione Webserver è attivata, il download di un file leggermente più grande avrà un rapporto di compressione migliore rispetto a molti file più piccoli (anche meno overhead http, roundtrip ecc ...). Immagino che questo risparmi sul caricamento della pagina iniziale, quindi la cache del browser inizia come indicato sopra.

ASP.NET a parte, questo screencast spiega i vantaggi in modo più dettagliato: http://www.asp.net/learn/3.5-SP1/video-296.aspx


2

Un altro vantaggio nascosto degli script esterni è che puoi facilmente eseguirli attraverso un controllo di sintassi come jslint . Ciò può salvarti da molti bug IE6 strazianti, difficili da trovare.


1

Nel tuo scenario sembra che scrivere le cose esterne in un file condiviso tra le pagine sia utile per te. Sono d'accordo con tutto quanto detto sopra.


1

Durante i primi prototipi, mantieni il tuo codice in linea per il vantaggio di una rapida iterazione, ma assicurati di renderlo tutto esterno quando raggiungi la produzione.

Oserei anche dire che se non riesci a posizionare tutto il tuo Javascript esternamente, allora hai un cattivo design sotto le tue mani e dovresti refactoring di dati e script


1

Google ha incluso i tempi di caricamento nelle sue misurazioni del posizionamento delle pagine, se sei molto in linea, ci vorrà più tempo perché gli spider scorrano attraverso la tua pagina, questo potrebbe influenzare il tuo posizionamento se devi includere molto. in ogni caso strategie diverse possono influire sulla tua classifica.


1

bene penso che dovresti usare in linea quando crei siti web a pagina singola poiché gli script non dovranno essere condivisi su più pagine


-3

Cerca sempre di usare js esterni poiché js inline è sempre difficile da mantenere.

Inoltre, è necessario utilizzare professionalmente un js esterno poiché la maggior parte degli sviluppatori consiglia di utilizzare js esternamente.

Io stesso uso js esterni.


2
Professionalmente richiesto? Perché? Chi lo dice?
Siyah,
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.