¿Cómo puedo forzar a los clientes a actualizar archivos JavaScript?


Actualmente estamos trabajando en una beta privada y por lo tanto todavía estamos en el proceso de hacer cambios bastante rápidos, aunque obviamente como el uso está empezando a aumentar, vamos a ralentizar este proceso. Dicho esto, un problema que nos encontramos es que después de enviar una actualización con nuevos archivos JavaScript, los navegadores cliente todavía usan la versión en caché del archivo y no ven la actualización. Obviamente, en una llamada de soporte, simplemente podemos informarles que hagan un ctrlF5 actualice para asegurarse de que obtienen los archivos actualizados del servidor, pero sería preferible manejar esto antes de ese momento.

Nuestro pensamiento actual es simplemente adjuntar un número de versión al nombre de los archivos JavaScript y luego, cuando se realicen cambios, incrementar la versión en el script y actualizar todas las referencias. Esto definitivamente hace el trabajo, pero actualizar las referencias en cada versión podría ser engorroso.

Como estoy seguro de que no somos el los primeros en lidiar con esto, pensé que lo tiraría a la comunidad. ¿Cómo se asegura de que los clientes actualicen su caché cuando actualiza su código? Si está utilizando el método descrito anteriormente, ¿está utilizando un proceso que simplifica el cambio?

Author: Jason Plank, 2008-08-28

21 answers

Por lo que sé, una solución común es agregar un ?<version> al enlace src del script.

Por ejemplo:

<script type="text/javascript" src="myfile.js?1500"></script>

Asumo en este punto que no hay una mejor manera que buscar-reemplazar para incrementar estos "números de versión" en todas las etiquetas del script?

Es posible que tenga un sistema de control de versiones hacer eso por usted? La mayoría de los sistemas de control de versiones tienen una forma de inyectar automáticamente el número de revisión en el check-in, por ejemplo.

Se vería algo así:

<script type="text/javascript" src="myfile.js?$$REVISION$$"></script>

Por supuesto, siempre hay mejores soluciones como esta.

 462
Author: Huppie,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-04-17 21:22:10

Añadir la hora actual a la URL es de hecho una solución común. Sin embargo, también puede administrar esto a nivel de servidor web, si lo desea. El servidor se puede configurar para enviar diferentes encabezados HTTP para archivos javascript.

Por ejemplo, para forzar que el archivo se almacene en caché durante no más de 1 día, debe enviar:

Cache-Control: max-age=86400, must-revalidate

Para la versión beta, si quieres forzar al usuario a obtener siempre la última, utilizarías:

Cache-Control: no-cache, must-revalidate
 75
Author: Chase Seibert,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-17 16:04:02

Google Page-Speed: No incluya una cadena de consulta en la URL para los recursos estáticos. La mayoría de los proxies, especialmente Squid up a través de la versión 3.0, no almacenan en caché los recursos con un "?"en su URL incluso si un encabezado Cache-control: public está presente en la respuesta. Para habilitar el almacenamiento en caché de proxy para estos recursos, elimine las cadenas de consulta de las referencias a recursos estáticos y, en su lugar, codifique los parámetros en los propios nombres de archivo.

En este caso, puede incluir la versión en URL ex: http://abc.com/ v1. 2 /script.js y use apache mod_rewrite para redirigir el enlace a http://abc.com/script.js. Cuando cambie la versión, el navegador del cliente actualizará el nuevo archivo.

 40
Author: Hắc Huyền Minh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-10-06 08:13:44

Esta respuesta es solo 6 años tarde, pero no veo esta respuesta en muchos lugares... HTML5 ha introducido Application Cache que se utiliza para resolver este problema. Estaba encontrando que el nuevo código de servidor que estaba escribiendo estaba fallando javascript antiguo almacenado en los navegadores de las personas, así que quería encontrar una manera de caducar su javascript. Utilice un archivo de manifiesto que se vea así:

CACHE MANIFEST
# Aug 14, 2014
/mycode.js

NETWORK:
*

Y genere este archivo con una nueva marca de tiempo cada vez que desee que los usuarios actualicen su caché. Como un lado tenga en cuenta que si agrega esto, el navegador no se recargará (incluso cuando un usuario actualice la página) hasta que el manifiesto lo indique.

 33
Author: amos,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-08-14 20:05:48

¿Qué tal agregar el tamaño de archivo como parámetro de carga?

<script type='text/javascript' src='path/to/file/mylibrary.js?filever=<?=filesize('path/to/file/mylibrary.js')?>'></script>

Así que cada vez que actualice el archivo, el parámetro "filever" cambia.

¿Qué tal cuando actualiza el archivo y su actualización resulta en el mismo tamaño de archivo? ¿cuáles son las probabilidades?

 25
Author: Erik Corona,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-12-02 00:45:42

No todos los navegadores almacenan archivos en caché con '?" en él. Lo que hice para asegurarme de que se almacenara en caché tanto como fuera posible, incluí la versión en el nombre del archivo.

Así que en lugar de stuff.js?123, hice stuff_123.js

Usé mod_redirect (creo) en apache a a have stuff_*.js para ir stuff.js

 18
Author: Echo,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-04-15 14:39:42

Para ASP.NET páginas que estoy usando

ANTES

<script src="/Scripts/pages/common.js" type="text/javascript"></script>

AFTER (force reload)

<script src="/Scripts/pages/common.js?ver<%=DateTime.Now.Ticks.ToString()%>" type="text/javascript"></script>

Añadiendo la fecha y hora.Ahora.Las garrapatas funcionan muy bien.

 9
Author: Ravi Ram,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-01-23 01:10:56

Para ASP.NET Supongo que la siguiente solución con opciones avanzadas (modo de depuración/liberación, versiones):

Archivos Js o Css incluidos de esta manera:

<script type="text/javascript" src="Scripts/exampleScript<%=Global.JsPostfix%>" />
<link rel="stylesheet" type="text/css" href="Css/exampleCss<%=Global.CssPostfix%>" />

Global.JsPostfix y Global.CssPostfix se calcula de la siguiente manera en Global.asax:

protected void Application_Start(object sender, EventArgs e)
{
    ...
    string jsVersion = ConfigurationManager.AppSettings["JsVersion"];
    bool updateEveryAppStart = Convert.ToBoolean(ConfigurationManager.AppSettings["UpdateJsEveryAppStart"]);
    int buildNumber = System.Reflection.Assembly.GetExecutingAssembly().GetName().Version.Revision;
    JsPostfix = "";
#if !DEBUG
    JsPostfix += ".min";
#endif      
    JsPostfix += ".js?" + jsVersion + "_" + buildNumber;
    if (updateEveryAppStart)
    {
        Random rand = new Random();
        JsPosfix += "_" + rand.Next();
    }
    ...
}
 5
Author: Ivan Kochurkin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-08-03 13:55:23

Si está generando la página que enlaza con los archivos JS, una solución simple es agregar la última marca de tiempo de modificación del archivo a los enlaces generados.

Esto es muy similar a la respuesta de Huppie, pero funciona en sistemas de control de versiones sin sustitución de palabras clave. También es mejor que agregar la hora actual, ya que eso evitaría el almacenamiento en caché incluso cuando el archivo no cambió en absoluto.

 4
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-17 16:03:06

La función getScript de jQuery también se puede usar para garantizar que un archivo js se cargue cada vez que se cargue la página.

Así es como lo hice:

$(document).ready(function(){
    $.getScript("../data/playlist.js", function(data, textStatus, jqxhr){
         startProgram();
    });
});

Compruebe la función en http://api.jquery.com/jQuery.getScript /

Por defecto, $.getScript () establece la configuración de caché en false. Esto añade un parámetro de consulta con marca de tiempo a la URL de la solicitud para garantizar que el navegador descarga el script cada vez que se solicita.

 2
Author: Michael Franz,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-10-10 20:53:10

Hemos estado creando un SaaS para los usuarios y proporcionándoles un script para adjuntar en su página web, y no fue posible adjuntar una versión con el script ya que el usuario adjuntará el script a su sitio web para funcionalidades y no puedo obligarlos a cambiar la versión cada vez que actualizamos el script

Por lo tanto, encontramos una manera de cargar la versión más reciente del script cada vez que el usuario llama al script original

el enlace del script proporcionado a usuario

<script src="https://thesaasdomain.com/somejsfile.js" data-ut="user_token"></script>

el archivo de script

if($('script[src^="https://thesaasdomain.com/somejsfile.js?"]').length !== 0) {
   init();
} else {
   loadScript("https://thesaasdomain.com/somejsfile.js?" + guid());
}

var loadscript = function(scriptURL) {
   var head = document.getElementsByTagName('head')[0];
   var script = document.createElement('script');
   script.type = 'text/javascript';
   script.src = scriptURL;
   head.appendChild(script);
}

var guid = function() {
    return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
        var r = Math.random() * 16 | 0, v = c == 'x' ? r : (r & 0x3 | 0x8);
        return v.toString(16);
    });
}

var init = function() {
    // our main code
}

Explicación:

El usuario ha adjuntado el script proporcionado a ellos en su sitio web y hemos comprobado si el token único adjunto con el script existe o no utilizando jQuery selector y si no lo carga dinámicamente con el token más nuevo (o versión)

Esto es llamar al mismo script dos veces lo que podría ser un problema de rendimiento, pero realmente resuelve el problema de forzar el script a no cargar desde el caché sin poner la versión en el enlace de script real dado al usuario o cliente

Descargo de responsabilidad: No lo use si el rendimiento es un gran problema en su caso.

 2
Author: Aman Singh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-11-08 08:27:59

Utilice una variable version GET para evitar el almacenamiento en caché del navegador.

Agregar ?v=AUTO_INCREMENT_VERSION al final de su url evita el almacenamiento en caché del navegador, evitando todos y cada uno de los scripts almacenados en caché.

 1
Author: Derek Adair,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-11-27 21:00:59

Mi colega acaba de encontrar una referencia a ese método justo después de que publiqué (en referencia a css) en http://www.stefanhayden.com/blog/2006/04/03/css-caching-hack / . Es bueno ver que otros lo están usando y parece funcionar. Supongo que en este punto que no hay una mejor manera que buscar-reemplazar para incrementar estos "números de versión" en todas las etiquetas de script?

 1
Author: AdamB,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-12-15 15:22:48

Aunque es específico del framework, Django 1.4 tiene esta funcionalidad que funciona de manera similar al enlace al sitio 'greenfelt' en la respuesta anterior

 1
Author: Taras,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 11:54:59

{[5] {} En[6]}PHP:

function latest_version($file_name){
    echo $file_name."?".filemtime($_SERVER['DOCUMENT_ROOT'] .$file_name);
}
{[5] {} En[6]}HTML:
<script type="text/javascript" src="<?php latest_version('/a-o/javascript/almanacka.js'); ?>">< /script>

Cómo funciona:

En HTML, escriba el filepath y el nombre como lo hace, pero solo en la función. PHP obtiene el filetime del archivo y devuelve el filepath+name+"?"+time del último cambio

 1
Author: user1944129,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-07-26 14:03:42

Cache Busting in ASP.NET Core a través de un ayudante de etiqueta se encargará de esto por usted y permitirá que su navegador mantenga scripts/css almacenados en caché hasta que el archivo cambie. Simplemente agregue la etiqueta ayudante asp-append-version = "true" a su etiqueta script (js) o link (css):

<link rel="stylesheet" href="~/css/site.min.css" asp-append-version="true"/>

Dave Paquette tiene un buen ejemplo y explicación de Cache busting aquí (al final de la página) Cache Busting

 1
Author: ccherwin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-06-29 22:30:36

Una solución es agregar una cadena de consulta con una marca de tiempo a la URL cuando se obtiene el recurso. Esto aprovecha el hecho de que un navegador no almacenará en caché los recursos obtenidos de las URL con cadenas de consulta en ellas.

Probablemente no quiera que el navegador no almacene en caché estos recursos; es más probable que los quiera en caché, pero desea que el navegador obtenga una nueva versión del archivo cuando esté disponible.

La solución más común parece ser para incrustar una marca de tiempo o un número de revisión en el propio nombre del archivo. Esto es un poco más de trabajo, porque su código necesita ser modificado para solicitar los archivos correctos, pero significa que, por ejemplo, la versión 7 de su snazzy_javascript_file.js (es decir, snazzy_javascript_file_7.js) se almacena en caché en el navegador hasta que lance la versión 8, y luego su código cambia para obtener snazzy_javascript_file_8.js en su lugar.

 0
Author: Richard Turner,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-17 14:31:11

¿La solución más simple? No deje que el caché del navegador en absoluto. Añada la hora actual (en ms) como una consulta.

(Usted todavía está en beta, por lo que podría hacer un caso razonable para no optimizar el rendimiento. Pero YMMV aquí.)

 0
Author: pcorcoran,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-17 15:55:01

La ventaja de usar un file.js?V=1 sobre un fileV1.js es que no necesita almacenar varias versiones de los archivos JavaScript en el servidor.

El problema que veo con file.js?V=1 es que puede tener código dependiente en otro archivo JavaScript que se rompe al usar la nueva versión de las utilidades de biblioteca.

En aras de la compatibilidad hacia atrás, creo que es mucho mejor usar jQuery.1.3.js para sus nuevas páginas y dejar que las páginas existentes usen jQuery.1.1.js, hasta que esté listo para actualizar las anteriores páginas, si es necesario.

 0
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-05-13 12:00:19

Una manera simple. Editar htaccess

RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_URI} \.(jpe?g|bmp|png|gif|css|js|mp3|ogg)$ [NC]
RewriteCond %{QUERY_STRING} !^(.+?&v33|)v=33[^&]*(?:&(.*)|)$ [NC]
RewriteRule ^ %{REQUEST_URI}?v=33 [R=301,L]
 0
Author: Goran Siriev,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-01-06 08:41:38

La práctica común hoy en día es generar un código hash de contenido como parte del nombre del archivo para forzar al navegador, especialmente IE, a recargar los archivos javascript o css.

Por ejemplo,

Proveedor. a7561fb0e9a071baadb9.js
principal. b746e3eb72875af2caa9.js

Generalmente es el trabajo para las herramientas de compilación como webpack. Aquí es más detalles si alguien quiere probar si está utilizando webpack.

 0
Author: schrodinger's code,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-09-27 11:00:25