2012-08-01 14 views
10

Tengo este extraño problema con Chrome. Con bastante frecuencia, parece almacenar en caché las solicitudes PUT.Chrome está almacenando en caché una solicitud HTTP PUT

Los detalles: Tengo una aplicación que usa backbone.js y cuando intento persistir algunos cambios en un modelo (la red troncal genera automáticamente una solicitud PUT), Chrome simplemente no envía esa solicitud al servidor. Funciona perfectamente bien en Firefox e IE (no he visto el problema en Safari hasta el momento).

Aquí hay una captura de pantalla de la pestaña Red de herramientas de desarrollador de Chrome. Como se puede ver, se devuelve la respuesta a la petición que desde el caché (la solicitud no golpea el servidor !!) Chrome caches PUT request

Aquí hay una captura de pantalla de los detalles del encabezado de esa misma petición. Una vez más, es evidente que Chrome no se molesta en enviar la solicitud PUT al servidor. Chrome cached PUT request header

La carga de la solicitud es datos JSON. ¿Alguna idea de por qué está sucediendo esto/qué estoy haciendo mal?

ACTUALIZACIÓN: Chromium ha confirmado que este es realmente un bug on it's end (gracias Jan Hančič).

solución temporal que terminó anulando Backbone.sync método y añadiendo una marca de tiempo a la cadena de consulta de PUT, POST y DELETE peticiones para que siempre son únicos:

if(!options.data && model && (method == 'create' || method == 'update' || method == 'delete')) { 
    params.url += (params.url.indexOf('?') == -1 ? '?' : '&') + '_=' + new Date().getTime(); 
} 
+2

¿Tiene esto sólo sucede si envía los datos en la solicitud PUT, que ya va a enviar antes o ¿esto también occure si cambia los datos que han de presentar y dar lugar a la solicitar nuevamente? –

+0

La respuesta del servidor no cambia, tal vez por eso está en caché. Como dijo Robin, cambie/corrija la solicitud – Zebra

+1

Los datos definitivamente cambian. Sin embargo, creo que no debería importar si los datos han cambiado o no. Un PUT realmente no es un tipo de solicitud cacheable. Está destinado a enviar datos al servidor, no a buscar datos. – anushr

Respuesta

4

utilizo parámetro adicional para evitar el almacenamiento en caché :

url += '?_dc=' + Math.random().toFixed(20).replace('.', ''); 

No interpreto este parámetro en el lado del servidor.

EDIT: Además de cromo hay una gran cantidad cosas podrían almacenar en caché peticiones - servidor proxy del usuario, por ejemplo. Creo que el parámetro de consulta adicional es una buena solución para evitar el almacenamiento en caché.

+0

Acepto que sería la solución adecuada. Intenté hacerlo, pero desafortunadamente, dado que usamos backbone.js, agregar parámetros de querystring adicionales es bastante difícil (a menos que alguien tenga sugerencias sobre cómo tener una carga de solicitud Y paramétrico de querystring con backbone) – anushr

+0

Puede implementar el método 'sync' para el modelo. Como puedo ver, puedes pasar 'url' con' options' al método 'Backbone.sync'. Consulte http://backbonejs.org/#Sync y la implementación 'sync' de la red troncal para obtener más detalles. Podrías envolver 'Backbone.sync' y hacer todas estas cosas en un solo lugar. –

+0

Terminé anulando 'Backbone.sync' e incluyendo la marca de tiempo (' url + = '? _ =' + New Date(). GetTime() ') siempre que hay una solicitud PUT, POST o DELETE (aparentemente Chrome tiene problemas with all 3) – anushr

0

Backbone utilice jQuery o Zepto para realizar la solicitud AJAX. Suponiendo que está utilizando jQuery, desactive la caché.

Ejecutar esto para establecer el caché fuera en la aplicación general por lo que no tendrá que preocuparse de caché:

$.ajaxSetup({ 
     cache : false 
}); 

Si mantener la memoria caché en la que es importante para su negocio, creo que se podría hacer algo así durante específica sin caché llama:

model.save({}, {cache:false}); 
+1

La propiedad 'cache' solo tiene efecto en las solicitudes' GET' (como debería ser). No hace nada para solicitudes 'PUT'. – anushr

+0

No lo creo, establezco el caché falso y veo que las solicitudes PUT tienen la consulta noCache. –

+0

No estoy muy seguro de dónde obtuvo esa información incorrecta acerca de que esa caché solo funciona para la solicitud GET, tal vez hoy va a sobrescribir en Backbone.Syncs, más adelante cuando solo pruebe $ .ajaxSetup comprenderá que funciona. Tengo muchos proyectos usando Backbone.js y jQuery y sé que esta línea es suficiente. –

Cuestiones relacionadas