只有当服务器中的文件发生变化时,如何在Apache中过期映像并强制重载

我有一个Apache2服务器上运行的PHP应用程序。 我开始使用HTML5 Boilerplate,而.htaccess包含所有图像的“1个月”过期策略。 例如:

 ExpiresByType image/jpeg "access plus 1 month" 

我的应用程序还允许用户用新的(在相同的名称和path下)replace现有的图像。 但是,一旦被replace,用户将继续看到旧的图像,直到页面被强制刷新(比如CtrlF5 )。

我从日志中注意到,从技术上讲,由于映像设置为从现在起1个月后过期,所以浏览器不会向服务器请求。 只有在浏览器强制刷新的时候,Apache2才会发出一个304 (如果文件没有改变),或者发送一个新的图像(如果改变的话)。

我想要的是一个简单的直接机制:

  • 保持图像从现在起1个月到期的现有设置。 如果浏览器已经拥有它,则不需要获取它。
  • 但是,如果图像被用户更新,则自动让浏览器获取新图像。 应该没有必要告诉用户强制刷新。
  • 最后一点之后,新图像的获取还必须扩展到其他用户或其他浏览器。

作为替代,我不介意是否可以有条件地将过期策略设置为“立即”用于特定path(其他文件夹中的图像必须遵循一般过期策略)。 我可以和众多的304一起生活。 我猜。

我不想简单地改变一个新的文件名。 文件名是dynamic生成的,有几个 – 跟踪他们的“新名字”会增加复杂性。 (虽然如果没有其他简单的解决scheme,我将不得不探讨这一点。)

你的要求很高:明确地configuration一些数据在一个月内是有效的,那么只要你改变了主意,那么它就不是那么快。 一般来说,你必须下定决心。

  • 如果304s不伤害你:缩短间隔可能是一个解决办法
  • 这个问题的stream行缓解涉及图像的时间戳参数:不要加载logo.png ,而是加载logo.png?t=20160327083700其中时间戳是通过您的所有应用程序静态化(并根据您的判断更新)或者文件的最后更改date(这将增加服务器端的负担)
  • 在您的评论之后,您可能也会成功添加path中其他地方的时间戳(以使您的图片名称保持不变):/ /20160327083700/logo.png 。 但是,请阅读关于过早优化的最后一段

只要你告诉大家,一个资源长期有效,不要惊讶,他们把你的话,并重复使用,直到时间结束。

对于上面的时间戳参数,我使用了一些可读的时间戳(例如今天)。 您可能只想使用自1970年以来的一个毫无格式的毫秒数,或者任何无格式化的值。 只需要随文件的每次更新而改变。

编辑:正如你在评论中所述,浏览器倾向于解释? 在作为caching旁路的URL中 – 并且更好地再次请求资源。 有了这个,你最好的select可能是缩短时间。 特别是当你说你会活下来的304s:下去"access plus 1 hour" (甚至10分钟)。 无论如何,这将是正确的做法: 声明内容可以被caching1个月, 当且仅当它可以被caching1个月。

顺便提一下,让我想起那句老话:“不成熟的优化是万恶之源” – 我敢打赌, "access plus 1 month"并不是来自任何性能调优会议,而是来自您的猜测。 而且,正如您在这个问题上看到的那样,这种过早的优化实际上会导致大量额外的工作来解决它引入的冲突。