Чи завантажують браузери javascript на кожній сторінці?


190

Чи браузери (IE та Firefox) розбирають пов'язані файли JavaScript щоразу, коли сторінка оновлюється?

Вони можуть кешувати файли, тому я здогадуюсь, що вони не будуть намагатися завантажувати їх кожен раз, але оскільки кожна сторінка, по суті, є окремою, я очікую, що вони зірвуть будь-який старий код і повторно розберуть його.

Це неефективно, хоча і цілком зрозуміло, але мені цікаво, чи сучасні браузери досить розумні, щоб уникнути кроку розбору в межах сайтів. Я думаю про випадки, коли сайт використовує бібліотеку javascript, наприклад ExtJS або jQuery тощо.


4
Мій 2c: Я відчуваю переваги продуктивності кешування розібраних файлів Javascript занадто малі, щоб це було значущою оптимізацією.
Itay Maman

2
З моїх орієнтирів, це насправді може мати значення. Наприклад, час завантаження jQuery становить близько 30 мс (на швидкій настільній машині), з яких 20% лише розбирають код у виконанні, а решта виконує його, тобто ініціалізує об'єкт jQuery в цьому випадку. Якщо ви користуєтеся мобільним телефоном і використовуєте дві-три бібліотеки, ця затримка може бути актуальною, оскільки виконання JavaScript блокується, а сторінка по суті порожня, доки кожен сценарій JS не завантажується в пам'ять.
djjeck

Відповіді:


338

Це деталі, які мені вдалося розкопати. Спершу варто зазначити, що хоча JavaScript зазвичай вважається інтерпретованим та працює на VM, це насправді не так у сучасних інтерпретаторів, які, як правило, збирають джерело безпосередньо в машинний код (за винятком IE).


Chrome: V8 Engine

V8 має кеш-компіляцію. Цей магазин зберігає JavaScript, використовуючи хеш-код джерела для до 5 сміттєзбірників. Це означає, що два однакові фрагменти вихідного коду поділять запис кешу в пам'яті незалежно від того, як вони були включені. Цей кеш не очищається при перезавантаженні сторінок.

Джерело


Оновлення - 19.03.2015

Команда Chrome опублікувала детальну інформацію про свої нові методи потокового передавання та кешування JavaScript .

  1. Потокове сценарій

Потоковий сценарій оптимізує розбір файлів JavaScript. [...]

Починаючи з версії 41, Chrome розбирає асинхронізацію та відкладає сценарії в окрему нитку, як тільки завантаження розпочалося. Це означає, що синтаксичний аналіз може закінчитися лише за кілька мілісекунд після закінчення завантаження, а результат завантаження сторінок на 10% швидше.

  1. Кешування коду

Зазвичай V8 двигун збирає JavaScript сторінки кожного відвідування, перетворюючи його на інструкції, які розуміє процесор. Цей скомпільований код відкидається, як тільки користувач відходить від сторінки, оскільки складений код сильно залежить від стану та контексту машини під час компіляції.

Chrome 42 запроваджує вдосконалену техніку зберігання локальної копії скомпільованого коду, так що, коли користувач повернеться на сторінку, кроки завантаження, розбору та компілювання можуть бути пропущені. При всіх завантаженнях сторінок це дозволяє Chrome уникати близько 40% часу на компіляцію та економить дорогоцінний акумулятор на мобільних пристроях.


Опера: Караканський двигун

На практиці це означає, що щоразу, коли збирається скласти програму скриптів, вихідний код якої ідентичний тим, який був недавно скомпільований іншою програмою, ми повторно використовуємо попередній вихід із компілятора і повністю пропускаємо етап компіляції. Цей кеш досить ефективний у типових сценаріях перегляду, коли одна сторінка завантажує сторінку за сторінкою з одного веб-сайту, наприклад, різні статті новин служби новин, оскільки кожна сторінка часто завантажує ту саму, іноді дуже велику бібліотеку сценаріїв.

Тому JavaScript кешується через перезавантаження сторінок, два запити на один і той же сценарій не призведуть до повторної компіляції.

Джерело


Firefox: SpiderMonkey Engine

SpiderMonkey використовує Nanojitяк власний бек-енд, компілятор JIT. Процес складання машинного коду можна побачити тут . Коротше кажучи, видається, що перекомпілювати сценарії під час завантаження. Однак якщо ми уважніше подивимось на внутрішні положення, Nanojitто побачимо, що монітор вищого рівня jstracer, який використовується для відстеження компіляції, може під час компіляції переходити через три етапи, забезпечуючи перевагу Nanojit:

Початковий стан монітора слідів - це моніторинг. Це означає, що людина-павук інтерпретує байт-код. Кожен раз, коли spidermonkey інтерпретує байт-код перескоку назад, монітор зазначає, скільки разів було перескочено значення цільового програмного лічильника (PC). Це число називається підрахунком звернень для ПК. Якщо кількість вражень для певного ПК досягає порогового значення, ціль вважається гарячою.

Коли монітор вирішує, що цільовий ПК є гарячим, він переглядає фрагменти фрагментів, щоб побачити, чи є фрагмент, у якому є власний код цього цільового ПК. Якщо він знайде такий фрагмент, він переходить у режим виконання. В іншому випадку він переходить у режим запису.

Це означає, що для hotфрагментів коду натурний код кешується. Це означає, що не потрібно буде перекомпілювати. Не зрозуміло, чи зберігаються ці хешовані нативні розділи між оновленнями сторінок. Але я б припустив, що вони є. Якщо хтось може знайти підтвердження для цього, то відмінно.

EDIT : Це було відзначено, що Mozilla розробник Борис Збарський заявив , що Gecko НЕ кеш скомпільована сценарії ще . Взято з цієї відповіді ТА .


Safari: JavaScriptCore / SquirelFish Engine

Я думаю, що найкращу відповідь на цю реалізацію вже дав хтось інший .

Наразі ми не кешуємо байт-кодом (або нативним кодом). Це
варіант, який ми розглядали, однак, наразі генерація коду є
тривіальною частиною часу виконання JS (<2%), тому
наразі ми цього не переслідуємо .

Про це написав Maciej Stachowiak , провідний розробник Safari. Тому я думаю, що ми можемо вважати це правдою.

Я не зміг знайти будь-яку іншу інформацію , але ви можете прочитати більше про поліпшення швидкості новітнього SquirrelFish Extremeдвигуна тут , або переглянути вихідний код тут , якщо ви відчуваєте пригоди.


IE: Двигун чакри

Немає поточної інформації щодо IE9 JavaScript Engine (Chakra) в цьому полі. Якщо хтось щось знає, будь ласка, прокоментуйте.

Це цілком неофіційне, але для більш старих реалізацій двигуна в IE, Ерік Ліпперта ( розробник МС JScript ) стверджує в блозі відповіді тут , що:

JScript Classic діє як скомпільована мова в тому сенсі, що перед запуском будь-якої програми JScript Classic ми повністю перевіряємо синтаксис коду, генеруємо дерево повного розбору та генеруємо байт-код. Потім ми запускаємо байт-код через інтерпретатор байт-коду. У цьому сенсі JScript кожен біт так само "компілюється", як і Java. Різниця полягає в тому, що JScript не дозволяє зберігати або перевіряти наш власний байт-код . Також байт-код набагато вищого рівня, ніж байт-код JVM - мова байт-коду JScript Classic трохи більше, ніж лінеаризація дерева розбору, тоді як байт-код JVM явно призначений для роботи на низькорівневій машині стека.

Це говорить про те, що байт-код не зберігається жодним чином, і, таким чином, байт-код не кешується.


10
+1, відмінна реєстрація. Однак, що стосується Firefox, перегляньте це питання StackOverflow, де розробник Mozilla Борис Збарський пояснює, що в даний час Gecko цього не робить.
cha0site

Дякую, я це бачив у своїх подорожах, але не зміг знайти жодних інших підтверджень Я відредагую відповідь.
Стрітення

1
Зауважте, що те, що було сказано про IE, було сказано в 2003 році: перший випуск двигуна JS IE9 був в IE9 в 2011 році.
gsnedders

Також Opera кешує байт-код JS над більш ніж просто перезавантаженням. (Однак генерований машинний код не кешований).
gsnedders

2
@ Життя Візьміть вищезазначене як джерело. (Я один із людей з команди Каракана.)
gsnedders

12

Opera це робить, як згадується в іншій відповіді. ( джерело )

Firefox (движок SpiderMonkey) не кешує байт-код. ( джерело )

WebKit (Safari, Konqueror) не кешує байт-код. ( джерело )

Я не впевнений в IE [6/7/8] або V8 (Chrome), я думаю, що IE може зробити якесь кешування, тоді як V8 може не зробити. IE є закритим вихідним кодом, тому я не впевнений, але у V8 це може не мати сенсу кешувати "компільований" код, оскільки вони складаються прямо до машинного коду.


1
IE6–8 майже точно не буде. IE9 може, але я не маю жодних доказів. Складений JS, ймовірно, ніде не кешується, оскільки він досить часто є досить великим.
gsnedders

@gsnedders: Я не впевнений, що IE8 технічно не може це зробити, здається, він занадто компілюється в байт-код (не офіційний, але закритий), тому немає технічної причини не кешувати це. IE9, здається, додає JIT для компіляції до рідного коду.
cha0site

2
Байт-код використовувався IE протягом… назавжди. Це нічого нового в IE8. Це просто лише те, що, даючи перекладачеві, робота перекладача набагато повільніше, ніж синтаксичний аналіз, це зовсім не має значення. IE9 має абсолютно новий (з нуля) двигун JS, тому між ними нічого не випливає.
gsnedders

3

Наскільки мені відомо, лише Opera кешує розроблений JavaScript. Дивіться розділ "Кешовані компільовані програми" тут .


дякую, чи є у вас більше деталей щодо інших сімейств браузерів?
ajreal

2

Нічого не варто, щоб Google Dart прямо вирішував цю проблему за допомогою "Знімки" - мета - прискорити ініціалізацію та час завантаження, завантаживши попередньо розроблену версію коду.

InfoQ має гарний запис @ http://www.infoq.com/articles/google-dart


0

Я думаю, що правильна відповідь була б "не завжди". Як я розумію, і браузер, і сервер грають роль у визначенні того, що відбувається кешування. Якщо вам справді потрібні файли для перезавантаження кожного разу, я думаю, ви повинні мати можливість налаштувати це зсередини Apache (наприклад). Звичайно, я припускаю, що браузер користувача може бути налаштований ігнорувати це налаштування, але це, мабуть, малоймовірно.

Тому я б міг уявити, що у більшості практичних випадків файли javascript самі кешуються, але динамічно повторно інтерпретуються щоразу, коли сторінка завантажується.


0

Браузер, безумовно, використовує кешування, але так, браузери аналізують JavaScript щоразу, коли сторінка оновлюється. Оскільки щоразу, коли сторінка завантажується браузером, вона створює 2 дерева 1.Статунове дерево та 2.рендреве дерево.

Це дерево візуалізації складається з інформації про візуальне розташування елементів купола. Тому щоразу, коли сторінка завантажується, javascript буде проаналізований і будь-які динамічні зміни javascript будуть, як позиціонування елемента dom, показ / приховування елемента, додавання / видалення призведе до того, що браузер відтворить дерево візуалізації. Але сучасні броузери, такі як FF та хром, поводяться з цим дещо інакше, вони мають концепцію поступового відображення, тому щоразу, коли js, як було зазначено вище, динамічні зміни, це призведе лише до того, що ці елементи знову і знову перефарбуються.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.