¿Cómo funciona realmente el cargador de cohetes de CloudFlare (y cómo puede un desarrollador garantizar la compatibilidad)?

31

CloudFlare tiene una tecnología innovadora llamada Rocket Loader (tanto en cuentas gratuitas como de pago). Pero, ¿cómo funciona realmente?

Tienen un par de páginas que describen la tecnología , pero no muchos detalles técnicos. Una característica clave es que hace que todo Javascript se cargue de manera no bloqueante (asincrónicamente) , ¡lo cual es una hazaña increíble! Esto significa que el HTML / CSS se puede representar sin esperar a que se carguen y ejecuten los scripts.

Diagrama del cargador de cohetes CloudFlare

¿Cómo es eso posible?

Seguramente no puede simplemente cambiar todas las <script>etiquetas para usar async="true"o defer="true"como esto rompería varias cosas ...

  1. Las secuencias de comandos aún deben cargarse en el orden correcto (por ejemplo, no puede cargar complementos jQuery hasta que se haya cargado la biblioteca jQuery).
  2. document.write()las llamadas en estos scripts deben funcionar ( aparentemente no hacen nada en los scripts asíncronos típicos ).
  3. ¿Qué pasa con el evento DOMContentLoaded? Si algunos scripts se cargan después de que esto se haya activado, ¿sus controladores de eventos no se activan?

Y como desarrollador, ¿hay algo más que deba tener en cuenta para garantizar que mis sitios / scripts / complementos sigan siendo compatibles con Rocket Loader?

Simon East
fuente

Respuestas:

27

CloudFlare describe cargador Rocket como este ...

Rocket Loader es un cargador de JavaScript asíncrono de uso general junto con un navegador virtual liviano que puede ejecutar de forma segura cualquier código JavaScript después de window.onload.

Rocket Loader hace muchas cosas:

  1. Asegura que todos los scripts en su página no bloqueen la carga del contenido de su página;
  2. Carga todos los scripts en su página, incluidos los scripts de terceros, de forma asíncrona;
  3. Agrupa todas las solicitudes de script en una sola solicitud sobre la cual se pueden transmitir múltiples respuestas;
  4. Utiliza LocalStorage en la mayoría de los navegadores y en casi todos los teléfonos inteligentes para almacenar scripts de manera más inteligente para que no se vuelvan a buscar a menos que sea necesario.

Eso es genial, pero ¿cómo lo logra?

Por lo que he leído y descubierto al ejecutar CloudFlare + Rocket Loader en mi propio sitio, funciona más o menos así ...

  1. Cuando se solicita una página HTML de un servidor CloudFlare, después de cargarla desde el servidor web de origen, reescribe todas las etiquetas de script en <script type="text/rocketscript">

  2. Los navegadores ignoran naturalmente las etiquetas de script ya que no entienden el formato "text / rocketscript"

  3. CloudFlare también inyecta un cloudflare.min.jsscript adicional en la página que realiza la magia ( ver la versión formateada aquí ). Este es el único script cargado inicialmente por el navegador (asincrónicamente).

  4. Este script analiza la página para cualquier script con el tipo "text / rocketscript".

  5. Luego verifica si alguno de estos scripts ya existe en el almacenamiento local del navegador. De lo contrario, realiza una solicitud AJAX para ellos (combinados en paquetes lógicos) desde el CDN de CloudFlare. No estoy muy seguro de cómo funciona cómo agrupar los scripts.

  6. Los servidores CDN recopilan los scripts (que pueden provenir de varios servidores diferentes: Google, Twitter, Facebook, otros CDN, etc.), ya sea de su caché o de los servidores de origen, y luego los combinan, minimizan y GZIP antes de enviarlos de vuelta al navegador

  7. Este navegador virtual al que se refieren debe ser simplemente un JavaScript que luego ejecuta cada uno de estos scripts en el orden correcto, haciendo cosas como:

    • Capturar todas las llamadas document.write()e inyectar ese contenido en la ubicación correcta de la página. (¿Posiblemente sobrescribiendo la write()función del navegador con una personalizada?)
    • Reactivar eventos como DOMContentLoaded y cargar .

De hecho, estoy bastante sorprendido de que funcione (aunque tal vez no siempre sea así ). Pero en circunstancias normales, no creo que los desarrolladores necesiten hacer nada especial para que su JavaScript sea compatible.

Esta es una wiki comunitaria, así que edite y agregue cualquier detalle adicional que falte.

Simon
fuente
2
Como se señaló anteriormente, esto puede ocasionar problemas y, en consecuencia, es posible que deba deshabilitarse, así que pruebe antes de la implementación.
dan
El navegador virtual posiblemente es una de DOM sombra como los utilizados por los marcos modernos como Backbone, angular, Ember, Knockout, etc.
Kaiser
3
Si vamos a cualquier página habilitada para cloudfare que tenga habilitada esta cosa de cohetes, podemos ver en la consola que de document.writehecho ha sido mutada. Me sale function (b,d,e,g,h){if(u.getActivated())return c.apply(f,arguments);try{return j[a].apply(f,arguments)}catch(i){return j[a](b,d,e,g,h)}}como el valor de la cadena. Entonces, la hipótesis que se document.writeha sobrescrito es realmente correcta.
user3459110
Traducción italiana de la publicación anterior, si alguien está interesado: klayz.com/community/…
Glauco Zega
55
Una cosa que he notado es que el cargador de cohetes usa document.write. Desde Chrome 53, DevTools emite advertencias para declaraciones problemáticas de document.write () y su uso desencadena una advertencia. De hecho, Chrome 53 + bloquearía el uso de document.write () de CloudFlare en una conexión 2G. Consulte Desarrolladores de Chrome para obtener más información developers.google.com/web/updates/2016/08/…
davemac