Tengo un problema extraño con IIS 7.
A veces parece devolver un 304 en lugar de un 200.
Aquí hay una solicitud de muestra capturada con Fiddler:
(Tenga en cuenta que el archivo solicitado aún no se encuentra en el caché de mi navegador).
GET https://[mysite]/Content/js/jquery.form.js HTTP/1.1 Accept: */* Referer: https://[mysite]/Welcome/News Accept-Language: sv-SE User-Agent: Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; InfoPath.2; OfficeLiveConnector.1.4; OfficeLivePatch.1.3; .NET4.0C; .NET4.0E) Accept-Encoding: gzip, deflate Host: [mysite] Connection: Keep-Alive Cache-Control: no-cache Cookie: ...
Tenga en cuenta que no hay If-Modified-Since o If-None-Match en la solicitud.
Pero aún así la respuesta es:
HTTP/1.1 304 Not Modified Cache-Control: public Expires: Tue, 02 Mar 2010 06:26:08 GMT Last-Modified: Mon, 22 Feb 2010 21:58:44 GMT ETag: "1CAB40A337D4200" Server: Microsoft-IIS/7.5 X-Powered-By: ASP.NET Date: Mon, 01 Mar 2010 17:06:34 GMT
¿Alguien tiene idea de lo que podría estar mal aquí?
Estoy ejecutando IIS 7 en Windows Web Server 2008 R2.
EDITAR:
He encontrado una solución alternativa, habilitar el almacenamiento en caché y luego deshabilitarlo en un nivel de extensión fue el truco para mí.
<configuration>
<system.webServer>
<caching enabled="true" enableKernelCache="true">
<profiles>
<add extension=".png" policy="DisableCache" kernelCachePolicy="DisableCache" />
<add extension=".gif" policy="DisableCache" kernelCachePolicy="DisableCache" />
<add extension=".js" policy="DisableCache" kernelCachePolicy="DisableCache" />
<add extension=".css" policy="DisableCache" kernelCachePolicy="DisableCache" />
</profiles>
</caching>
<staticContent>
<clientCache cacheControlMode="NoControl" />
</staticContent>
</system.webServer>
</configuration>
windows-server-2008
iis-7
asp.net
Ola Herrdahl
fuente
fuente
Respuestas:
De acuerdo con la sección 14.9 de la especificación HTTP1.1 , la
no-cache
directiva para el encabezado Cache-Control solo es imposible para el servidor de origen, lo que significa que IIS está ignorando el encabezado en su solicitud.La Sección 14.9.1 define
public
,private
yno-cache
como las directivas que restringen lo que se puede almacenar en caché, que solo puede imponer el servidor.Si no desea que su archivo .js se almacene en caché, deberá configurar la
no-cache
directiva en la aplicación (es decir, el código ASP.NET) o deberá cambiar elCache-Control
encabezado en la solicitud para usar lano-store
directiva en lugar deno-cache
.EDITAR:
según su comentario, sí, supuse que no quería que el archivo se almacenara en caché. El 304, entonces, podría venir como resultado de que el archivo esté en una de las cachés internas de IIS. Echa un vistazo a estos:
fuente
He tenido el mismo problema durante un tiempo y he desactivado todo el almacenamiento en caché ... Sin embargo, instalé el módulo de compresión para IIS7 en algún momento que, de manera predeterminada, había habilitado la compresión de archivos estáticos en mis sitios existentes. Desactivé toda la compresión de los sitios afectados y ahora parece que están trabajando con madera fina .
fuente
También estábamos experimentando este error pero estábamos usando una biblioteca de administración de activos (Cassette). Después de una extensa investigación de este problema, descubrimos que la causa raíz de este problema es con una combinación de ASP.NET, IIS y Cassette. No estoy seguro de si este es su problema (usando la
Headers
API en lugar de laCache
API), pero el patrón parece ser el mismo.Bug # 1
Cassette establece el
Vary: Accept-Encoding
encabezado como parte de su respuesta a un paquete ya que puede codificar el contenido con gzip / deflate:Sin embargo, el caché de salida de ASP.NET siempre devolverá la respuesta que se almacenó en caché primero. Por ejemplo, si la primera solicitud tiene
Accept-Encoding: gzip
y Cassette devuelve contenido comprimido, la caché de salida de ASP.NET almacenará en caché la URL comoContent-Encoding: gzip
. La siguiente solicitud a la misma URL pero con una codificación aceptable diferente (por ejemploAccept-Encoding: deflate
) devolverá la respuesta almacenada en cachéContent-Encoding: gzip
.Este error se debe a que Cassette usa la
HttpResponseBase.Cache
API para establecer la configuración de caché de salida (por ejemploCache-Control: public
) pero usa laHttpResponseBase.Headers
API para establecer elVary: Accept-Encoding
encabezado. El problema es que el ASP.NETOutputCacheModule
es no consciente de las cabeceras de respuesta; solo funciona a través de laCache
API. Es decir, espera que el desarrollador use una API invisiblemente acoplada en lugar de solo HTTP estándar.Bug # 2
Cuando se usa IIS 7.5 (Windows Server 2008 R2), el error n. ° 1 puede causar un problema separado con el kernel IIS y las memorias caché del usuario. Por ejemplo, una vez que un paquete se almacena en caché con éxito
Content-Encoding: gzip
, es posible verlo en el caché del kernel IIS connetsh http show cachestate
. Muestra una respuesta con código de estado 200 y codificación de contenido de "gzip". Si la siguiente solicitud tiene una codificación aceptable diferente (pAccept-Encoding: deflate
. Ej. ) Y unIf-None-Match
encabezado que coincide con el hash del paquete, la solicitud en el kernel de IIS y las cachés de modo de usuario se considerarán como incorrectas . Por lo tanto, haciendo que Cassette maneje la solicitud, que devuelve un 304:Sin embargo, una vez que el kernel y los modos de usuario de IIS procesen la respuesta, verán que la respuesta para la URL ha cambiado y la caché debe actualizarse. Si se
netsh http show cachestate
vuelve a verificar el caché del kernel IIS , la respuesta 200 en caché se reemplaza por una respuesta 304. Todas las solicitudes posteriores al paquete, independientemente deAccept-Encoding
yIf-None-Match
devolverán una respuesta 304. Vimos los efectos devastadores de este error donde todos los usuarios recibieron un 304 para nuestro script central debido a una solicitud aleatoria que tuvo un inesperadoAccept-Encoding
yIf-None-Match
.El problema parece ser que el caché de IIS y las memorias caché de modo de usuario no pueden variar según el
Accept-Encoding
encabezado. Como prueba de esto, al usar laCache
API con la solución a continuación, las memorias caché del núcleo IIS y del modo de usuario parecen omitirse siempre (solo se usa la memoria caché de salida ASP.NET). Esto se puede confirmar comprobando quenetsh http show cachestate
está vacío con la solución a continuación. ASP.NET se comunica con el trabajador de IIS directamente para habilitar o deshabilitar selectivamente el kernel de IIS y las cachés en modo de usuario por solicitud.No pudimos reproducir este error en versiones más nuevas de IIS (por ejemplo, IIS Express 10). Sin embargo, el error # 1 todavía era reproducible.
Nuestra solución original para este error fue deshabilitar el almacenamiento en caché del modo IIS del kernel / usuario solo para solicitudes de Cassette como se mencionó anteriormente. Al hacerlo, descubrimos el error n. ° 1 al implementar una capa adicional de almacenamiento en caché frente a nuestros servidores web. La razón por la que funcionó el hack de cadena de consulta es porque
OutputCacheModule
registrará un error de caché si laCache
API no se ha utilizado para variar en función deQueryString
y si la solicitud tiene unQueryString
.Solución alterna
De todos modos, hemos planeado alejarnos de Cassette, por lo que en lugar de mantener nuestra propia bifurcación de Cassette (o tratar de fusionar un PR), optamos por usar un módulo HTTP para solucionar este problema.
Espero que esto ayude a alguien 😄!
fuente